diff options
Diffstat (limited to '_posts')
29 files changed, 1251 insertions, 20 deletions
diff --git a/_posts/2009-02-07-techtalk-einen-gameboy-auf-dem-pc.md b/_posts/2009-02-07-techtalk-einen-gameboy-auf-dem-pc.md index 2c556d6..f02d62a 100644 --- a/_posts/2009-02-07-techtalk-einen-gameboy-auf-dem-pc.md +++ b/_posts/2009-02-07-techtalk-einen-gameboy-auf-dem-pc.md @@ -103,19 +103,13 @@ UPDATE (30.4.2009): ### Emulatoren -- <a href="https://de.wikipedia.org/wiki/Emulator">Emulator</a> auf -Wikipedia -- <a href="https://emulator-zone.com/">Emulator Zone</a> Eine -Übersicht über Spielkonsolenemulatoren. -- _VisualBoyAdvance (toter Link entfernt)_ -Homepage des Emulators "VisualBoyAdvance" +- <a href="https://de.wikipedia.org/wiki/Emulator">Emulator</a> auf Wikipedia +- <a href="https://emulator-zone.com/">Emulator Zone</a> Eine Übersicht über Spielkonsolenemulatoren. +- _VisualBoyAdvance (toter Link entfernt)_ Homepage des Emulators "VisualBoyAdvance" - [SourceForge-Projektseite vom Emulator](https://sourceforge.net/projects/vba/) ### Spiele -- <a href="https://de.wikipedia.org/wiki/ROM_%28Spielmodul%29">ROM</a> -auf Wikipedia -- _PDRoms / Gameboy (toter Link entfernt)_ -Legale ROMs für den GameBoy -- _PDRoms / GameBoy Advance (toter Link entfernt)_ -Legale ROMs für den GameBoy Advance +- <a href="https://de.wikipedia.org/wiki/ROM_%28Spielmodul%29">ROM</a> auf Wikipedia +- _PDRoms / Gameboy (toter Link entfernt)_ Legale ROMs für den GameBoy +- _PDRoms / GameBoy Advance (toter Link entfernt)_ Legale ROMs für den GameBoy Advance diff --git a/_posts/2014-06-16-berlicon-11.md b/_posts/2014-06-16-berlicon-11.md index 7993746..4286477 100644 --- a/_posts/2014-06-16-berlicon-11.md +++ b/_posts/2014-06-16-berlicon-11.md @@ -12,7 +12,7 @@ description: "Erfahrungsbericht einer Furry-Convention. Berlicon 11 (im Jahre 20 So. Die Berlicon 11 ist vorbei. Und ich bin froh, dabei gewesen zu sein. Als Erinnerungsstütze - vor allem für mich - ist dieser Blogeintrag. Erwartet daher auch bitte keine journalistische Qualität. (Insbesondere angesichts der Uhrzeit) -<p style="font-weight: bold;">Tag 1</p> +<p class="bold">Tag 1</p> Die Anreise verlief ohne größere Probleme. Letztes Jahr bin ich zwar auch per Fernbus angereist, dieses Jahr waren allerdings keine Vollsperrung oder sonstige größere Verzögerungen auf der Strecke. Nur ein kleiner Stau, der uns um 10 Minuten verzögert hat. Da ich letztes Jahr schon an der Haltestelle ZOB/ICC in Berlin war, wusste ich zumindest ungefähr, wie es da aussieht. Und ich hätte damals nie gedacht, dass ich das sage, aber: Gott sei Dank habe ich ein Smartphone. So hatte ich sowohl Fahrpläne der BVG als auch eine Übersicht der Haltestellen dabei - auch wenn es kleinere Probleme beim Wechsel von S-Bahn zu Bushaltestelle gab. Auch bin ich froh, einen Rollkoffer zu haben. So eine Tasche zu schleppen wäre mir zu anstrengend. @@ -30,7 +30,7 @@ Weiterhin habe ich an diesem Abend ein neues Spiel kennengelernt, dass mich zuti Oh, außerdem war an dem Abend noch Karaoke angesagt. Ich hab mich an "Broken Wings" gewagt. Es war hoffentlich nicht allzu schlimm... -<p style="font-weight: bold;">Tag 2</p> +<p class="bold">Tag 2</p> Freitag, der erste "volle" Con-Tag. Was war da los? So richtig weiß ich es auch nicht mehr, größtenteils war ich wohl mit MahJong beschäftigt. Ansonsten waren an dem Tag noch die Suiter-Spiele. An denen ich mangels Suit nur als Zuschauer und Helfer teilgenommen habe, Weiterhin ist Freitags auf Berlicon (soweit ich mich zurück erinnere) ja immer BBQ-Abend. Und es war der Abend, an dem ich mich das erste verflucht habe, dass ich keine Jacke mitgenommen habe. Also habe ich mir zwei oder drei T-Shirts unter einen - relativ dünnen - Pullover angezogen. Positiv lässt sich jedoch sagen, dass es keine Mückenplage gab. Das BBQ verbrachte ich mit Essen und Gedulds/Kniffelspielen, die jemand mitgebracht hatte. @@ -42,7 +42,7 @@ Weiterhin ist Freitags auf Berlicon (soweit ich mich zurück erinnere) ja immer Nach dem BBQ war es Zeit für "Go get it". Tatsächlich hatte sich eine Fünfergruppe (ich verfluche mich gerade wieder für mein schlechtes Namensgedächtnis, Ich (uvok), Meomar, Egnur, Alvord und noch jemand, deren Name mir nicht mehr einfällt) zusammengefunden, nachdem ich mir dachte, dass man dieses Jahr doch mal mitmachen könnte. Nach der Schnitzeljagd war auch das Kältegefühl verschwunden :3 Ein wenig hin- und herrennen wärmt doch unglaublich auf. -<p style="font-weight: bold;">Tag 3</p> +<p class="bold">Tag 3</p> Wie sich herausstellte, hat unsere Gruppe den 3. Platz belegt - von dreien... Naja, ich muss sagen, ich hätte uns besser eingeschätzt. Da ich in ein Gespräch vertieft war, habe ich nicht gemerkt, dass es mit der Auswertung los ging. Daher weiß ich auch nicht was der Grund war. Aber hey, eine schöne Medaille habe ich trotzdem bekommen :3 {% image @@ -54,10 +54,10 @@ Nachmittags war dann ein Suitwalk durch den Grunewald angesetzt. Dem habe ich mi Abends war dann wieder PFR angesagt. Und PFR-Essen: Kartoffelsuppe gefolgt von einem wunderbaren gefüllten Schweinefilet. Ich kann gar nicht in Worte fassen, wie sehr mit schon der erste Bissen geschmeckt hat. @.@ Die Sendung über verbrachte ich jedenfalls - wieder einmal - mit Mahjong. -<p style="font-weight: bold;">Tag 4</p> +<p class="bold">Tag 4</p> So schnell kann es gehen, dann ist die Con schon vorbei. Abschied nehmen fällt immer schwer. So war am Tag der Abreise für mich nicht mehr viel los, aufstehen, bisschen übers Gelände laufen, frühstücken, noch ein wenig plauschen, Zimmer räumen, weiter plauschen, und dann ging es nach der Verabschiedung auch schon los. -<p style="font-weight: bold;">Abenteuerliche Abreise</p> +<p class="bold">Abenteuerliche Abreise</p> Wie Anfangs schon erwähnt, ist so ein Smartphone schon ein Segen. Nicht jedoch, wenn der Akku leer ist... So begab es sich, dass ich mit vom Berlicon-Gelände zum ZOB/ICC eine Busverbindung herausgesucht habe. Nur, an der Umsteigehaltestelle angekommen musste ich feststellen, dass die Linie 104 wohl nicht fuhr. Leider auf die schmerzhafte Weise: Warten, bis man merkte, dass der Bus schon 2x nicht kam, und es zu spät war, rechtzeitig am ZOB zu sein. An der Hotline von meinfernbus ging auch keiner ran, obwohl der Fahrschein versprach, dass dort jemand Montag-Sonntag 0-24h erreichbar wäre. :( @@ -71,7 +71,7 @@ Im Nachhinein betrachtet zucke ich aber mit der Schulter und sage mir: "So what? An dieser Stelle ein riesengroßes <b>Danke</b> an die Orga, aber auch an alle Teilnehmer, die die Con zu dem gemacht hat, was sie war. -<p style="font-weight: bold;">Sonstiges</p> +<p class="bold">Sonstiges</p> Hier noch zwei Bilder vom Congelände. Ich hab mal die Panorama-Funktion meines Smartphones ausprobiert. {% linked_image diff --git a/_posts/2021-03-23-winvm.md b/_posts/2021-03-23-winvm.md index 528d636..3ee73f4 100644 --- a/_posts/2021-03-23-winvm.md +++ b/_posts/2021-03-23-winvm.md @@ -4,6 +4,7 @@ title: Windows VM under Devuan with QEMU / libvirt date: 2021-03-23 20:32 +0100 categories: tech description: How to run a Windows VM under Devuan with QEMU / libvirt +lang: en --- So, I'm running Devuan Beowulf (Debian Buster based). Recently, I was in the need of running a diff --git a/_posts/2021-04-25-networkstuff.md b/_posts/2021-04-25-networkstuff.md index 3152f3f..7b2cff6 100644 --- a/_posts/2021-04-25-networkstuff.md +++ b/_posts/2021-04-25-networkstuff.md @@ -4,6 +4,7 @@ title: Network stuff date: 2021-04-25 21:50 +0200 categories: tech description: "I do some experiments with networking stuff. Proxmox and running OpenWRT in a VM." +lang: en --- Been a long time. diff --git a/_posts/2021-06-03-fakir-teardown.md b/_posts/2021-06-03-fakir-teardown.md index 1de8bf9..75f609d 100644 --- a/_posts/2021-06-03-fakir-teardown.md +++ b/_posts/2021-06-03-fakir-teardown.md @@ -3,6 +3,7 @@ layout: post title: Fakir Robert Teardown date: 2021-06-03 20:39 +0200 description: Ein Teardown eines alten Staubsauger-Roboters +lang: de --- Da ich mir demnächst mal einen neuen gebrauchten Saugroboter holen werde, diff --git a/_posts/2021-06-27-wpa-enterprise-unifi.md b/_posts/2021-06-27-wpa-enterprise-unifi.md index 61c49a7..36b9e6e 100644 --- a/_posts/2021-06-27-wpa-enterprise-unifi.md +++ b/_posts/2021-06-27-wpa-enterprise-unifi.md @@ -4,6 +4,7 @@ title: WPA Enterprise mit Unifi Access Points date: 2021-06-27 20:28 +0200 categories: tech description: "Wie man WPA Enterprise einrichtet, mit Unifi WiFi Access Points und Software, die unter Linux läuft" +lang: de --- Ich hab mal einen kurzen Artikel geschrieben, wie man WPA Enterprise diff --git a/_posts/2021-09-22-problems-updating-proxmox.md b/_posts/2021-09-22-problems-updating-proxmox.md index 3885b79..7353d67 100644 --- a/_posts/2021-09-22-problems-updating-proxmox.md +++ b/_posts/2021-09-22-problems-updating-proxmox.md @@ -2,6 +2,7 @@ layout: post title: Network gone after updating Proxmox date: 2021-09-22 20:59 +0200 +lang: en --- So, after upgrading Proxmox from version 6.x to 7.x, the network diff --git a/_posts/2021-10-28-rant-devuan-upgrade.md b/_posts/2021-10-28-rant-devuan-upgrade.md index 100dd3b..c3da9b0 100644 --- a/_posts/2021-10-28-rant-devuan-upgrade.md +++ b/_posts/2021-10-28-rant-devuan-upgrade.md @@ -3,6 +3,7 @@ layout: post title: 'Rant: Devuan Upgrade' date: 2021-10-28 19:58 +0200 categories: tech +lang: en --- Gna. So I upgraded my Devuan installation from Beowulf to Chimaera. Process was a bit tricky, diff --git a/_posts/2022-01-20-server-stuff.md b/_posts/2022-01-20-server-stuff.md index 40d39a1..f5f053f 100644 --- a/_posts/2022-01-20-server-stuff.md +++ b/_posts/2022-01-20-server-stuff.md @@ -3,7 +3,7 @@ layout: post title: Server stuff date: 2022-01-20 18:55 +0100 category: tech -language: en +lang: en description: "I experiment with SPF, DMARC and DKIM." --- diff --git a/_posts/2022-04-03-backporting-pipewire-in-devuan.md b/_posts/2022-04-03-backporting-pipewire-in-devuan.md index 1d20df2..c0a9fe3 100644 --- a/_posts/2022-04-03-backporting-pipewire-in-devuan.md +++ b/_posts/2022-04-03-backporting-pipewire-in-devuan.md @@ -3,7 +3,7 @@ layout: post title: Backporting Pipewire in Devuan date: 2022-04-03 17:45 +0200 category: tech -language: en +lang: en --- **Update 2023-09-07**: With Devuan Daedelus Pipewire is in the diff --git a/_posts/2024-08-02-use-a-second-signal-account-kinda.md b/_posts/2024-08-02-use-a-second-signal-account-kinda.md index 90b7687..a9753ba 100644 --- a/_posts/2024-08-02-use-a-second-signal-account-kinda.md +++ b/_posts/2024-08-02-use-a-second-signal-account-kinda.md @@ -2,6 +2,7 @@ layout: post title: Use a second Signal account (kinda) date: 2024-08-02 18:48 +0200 +last_modified_at: 2025-05-29 16:50 +0200 lang: en categories: ["tech"] description: "How to use a second Signal account on your Smartphone" @@ -52,3 +53,9 @@ already, so not a huge disadvantage). But hey, maybe this is still useful for some people. +**Update 2025-05-29** + +Actually, you can also use multiple accounts on the Desktop client. +Since it's just an Electron app (?), you only need a second Launcher +with the executable and arguments being +`/opt/Signal/signal-desktop --user-data-dir=<whatever you want> %U`. diff --git a/_posts/2024-09-04-convention-report-east-12-2024.md b/_posts/2024-09-04-convention-report-east-12-2024.md index 7c71898..31785a8 100644 --- a/_posts/2024-09-04-convention-report-east-12-2024.md +++ b/_posts/2024-09-04-convention-report-east-12-2024.md @@ -3,6 +3,7 @@ layout: post title: 'Convention Report: EAST 12 (2024)' date: 2024-09-04 20:00 +0200 description: My convention report of the furry convention "EAST 12" in 2024 +lang: en --- It's time for another convention report. I've been going to the EAST convention since EAST 7 (except EAST 10, which was diff --git a/_posts/2025-01-01-2024-review.md b/_posts/2025-01-01-2024-review.md index 5d0d433..80cf09d 100644 --- a/_posts/2025-01-01-2024-review.md +++ b/_posts/2025-01-01-2024-review.md @@ -4,6 +4,7 @@ title: '2024: Review' date: 2025-01-01 10:47 +0100 lang: "en" categories: "life" +description: "I muse over what I did in 2024" --- So, already wanted to do this yesterday, but I think today works as well. diff --git a/_posts/2025-01-01-my-static-blog-now-has-activitypub.md b/_posts/2025-01-01-my-static-blog-now-has-activitypub.md index 62feced..1a5af4d 100644 --- a/_posts/2025-01-01-my-static-blog-now-has-activitypub.md +++ b/_posts/2025-01-01-my-static-blog-now-has-activitypub.md @@ -5,6 +5,7 @@ date: 2025-01-01 18:56 +0100 last_modified_at: 2025-01-01 19:34 +0100 categories: ["tech"] lang: "en" +description: "A short praise for Hatsu, thanks to which my posts now appear in the Fediverse." --- Thanks to [Hatsu](https://github.com/importantimport/hatsu), my blog now has ActivityPub support. diff --git a/_posts/2025-01-12-migrating-dns-servers.md b/_posts/2025-01-12-migrating-dns-servers.md new file mode 100644 index 0000000..a0bf09b --- /dev/null +++ b/_posts/2025-01-12-migrating-dns-servers.md @@ -0,0 +1,289 @@ +--- +layout: post +title: Migrating DNS providers +lang: en +categories: tech +date: 2025-01-12 16:49 +0100 +last_modified_at: 2025-01-15 19:57 +0100 +redirect_from: /2025/01/2025-01-12-migrating-dns-servers.html +description: "An in-depth look into how to switch DNS providers without downtime." +--- + +**Update 2025-01-15:** Add links to tools, add clarification for DNSSEC tool, +add clarification for validation errors/warnings. + +## Preface + +[As I posted on Mastodon](https://furry.engineer/@uvok/113780013806190576), + +* the DNS registrar (where you register the domain at), +* the DNS hoster / provider (which is responsible for answering DNS requests for + your domain) and +* the (web) hosting service + +can be three different entities, even though for most beginner projects these +are the same. + +I either bought or migrated my domain over to [INWX](https://www.inwx.de/en) +quite some while ago. However, their web interface for editing records is a bit +clunky. And while they do provide an API, it's a bit awkward (XML based, and +yes, there are ready-made packages for various programming languages). [^1] + +With [DN42](https://blog.uvokchee.de/dn42.html), I already used +[PowerDNS](https://doc.powerdns.com/authoritative/) a lot. I actually just use +edit-zone and edit the zone[^2] in an editor, that's my preferred way. Definitely +preferred to some web interface. It would be nice to do this to my main domains +as well. Also, this is another nice "have a technical task to procrastinate +other stuff" thing ;3. Well, I like playing with tech. This is by no means +essential. + +## Glossary + +Quick and dirty glossary, for the purpose of reading this article. It's not +100% accurate and complete, but should be enough to understand the article. + +* **Domain Name**: Basically "the name of a server" (what you see in the address + bar of the browser, e.g. "blog.uvokchee.de"). +* **DNS**: The "Domain Name System". Very simplified, translates domain names + to IP addresses (which computers use to connect to each other). + To be more precise, it's like a lookup in a database (-> DNS record). +* **TLD**: Top-Level Domain. It's "the last part of the domain name" (e.g. + ".de"). +* **Registry**: These run the TLDs. +* **Registrar**: These sell you domain names from the registries. As an "end + user", you can't talk to a registry yourself. +* **DNSSEC**: DNS is a plain-text, insecure protocol, from way back when the + internet consisted of a handful of trustworthy people. DNSSEC tries to prevent + malicious parties from sending wrong information in response to DNS requests. + It does so by signing the responses with a cryptographic key, of which the + public part is stored in the registry. +* **NSEC, NSEC3**: Basically these are "negative replies", i.e. "this domain + does not exist". These are signed as well. If not present, malicious parties + could send back replies to sites they don't want to be reachable as "doesn't + exist" all the time. +* **Zone**: A zone file contains all the -> DNS records for a specific domain. +* **DNS record**: Like "a row in the database" which belongs to your domain. Can + be an address, but also things like text, PGP keys, pointer to other domain + names, etc.. +* **TTL**: Time To Live. The time (in seconds) a reply to a DNS request may be + cached by a server. For example, a TTL of 3600 seconds means that a (caching) + DNS server can cache a record for 1 hour before checking with the + -> authoritative server again. +* **Authoritative Server:** The DNS server that holds the official and most + up-to-date records for a specific domain. + * **Primary**: The primary source of truth. + * **Secondary**: Mirrors the information from the primary. There can be more + than one. +* **Recursion**: DNS is hierarchical. There are fixed "root servers" which serve + the nameservers for all the TLDs. The TLDs provide the nameservers for the + domains "below them". A recursive server "walks along this path" to answer + requests. At some point, it arrives at the authoritative server. +* **Bogus reply**: A reply with invalid signature, either because it has been + tampered with, or because of wrong configuration. +* **AXFR**: A request type for a -> Domain zone transfer. +* **Domain Zone Transfer**: The process of copying the contents of a zone from + one DNS server to another. + +## Migration and DNSSEC + +So, why not migrate my domain over to my PowerDNS setup? Well, I want some +availability, and I don't trust myself enough not to fuck things up. When my +server is shut down, DNS requests should still be answered. But hey, that's +where secondaries come in! So, I manage the zone on my server, as primary, and +let another provider mirror its contents. These will actually "serve the zone". + +Now, only… there's the "problem" of DNSSEC, in conjunction with the DNS +propagation time and TTLs. If I simply set the nameservers (in the de zone) to +a newly created zone by PowerDNS, the DNSSEC keys will be either not present, +or different. I can't set *additional* keys at INWX easily, I can only switch +to manual keys (by switching off DNSSEC first). Which would lead to a downtime +of up to one day, because people requesting records from my domain (such as +myself) would receive bogus replies in that time. I want to avoid that. + +## Steps for migration + +But, I think I found a solution for that. This are the steps which I had to take +for the registrar INWX and my uvokchee.de domain. The process might be different +for other TLDs and other registrars. + +1. Download the zone data from the INWX web interface +1. Create the zone in PowerDNS and set various settings + + #!/bin/bash + zone="example.com" + pdnsutil create-zone $zone + pdnsutil set-kind $zone primary + pdnsutil secure-zone $zone + pdnsutil set-presigned $zone + pdnsutil set-meta $zone ALLOW-AXFR-FROM <ip of secondaries> + # optional? see below for a discussion + pdnsutil set-nsec3 $zone $parameters +1. Filter and import the zone. PowerDNS will actually complain about the NSEC3 + records otherwise once you open the zone in your editor. + + # any other regex that filters only NSEC3 records, but not RRSIG NSEC3, + # work as well + grep -vw "IN NSEC3" ./dl-zone.txt > imp-zone.txt + pdnsutil load-zone $zone ./imp-zone.txt + + This should keep the RRSIGs for the NSEC3 records. This doesn't help with + the errors I receive later, though… + +1. Set up the secondaries. I went with [Hurricane + Electric](https://dns.he.net/), but I had to write them an e-mail. I couldn't + add the zone as secondary myself, because the web interface requires the + nameservers in the parent zone (?) already to be set to HE, but I wanted a + zero-downtime migration. +1. Wait for the DNS provider to AXFR. +1. (optional) check with [dnsviz](https://dnsviz.net/) whether you get any + errors. You should set the nameserver on the "Analyze" tab, and then set the + "Additional trusted keys:" to what `dig example.com DNSKEY` tells you. At + this point, I got warnings/errors regarding the "Denial of existence" / + NSEC3 records, and some errors because the RRSIGs can't be checked. (Once + you set a manual nameserver, the tool doesn't seem to check for the parent + zone anymore? I'm unclear on that). +1. Try to set the new nameservers (nsx.he.net) in the registry (e.g. DENIC) via + the INWX web interface ("external nameservers"). +1. Receive an "UPDATE FAILED". Read the error message. + + ERROR: 53300102912 Nameserver error [ERROR: 118 Inconsistent set of NS + RRs (NS, IP, NS host names) (ns5.he.net, 2001:470:500::2, ['ns.inwx.de', + 'ns2.inwx.de', 'ns3.inwx.eu'])] + + Realize you fucked up. + You need to set the new nameservers within your own zone first. This seems + to be a requirement for DENIC at any case. +1. Add the NS entries to the HE nameservers within your zone in the INWX web + interface. [^4] +1. Download and import the zone file again. Wait for the AXFR. +1. Retry sending the nameservers to the registry. Wait until success. +1. At this point, I checked again with dnsviz. With the default options, + everything was fine. However, when I enabled the "Denial of existence:" + option, I received some *extremely scary looking error messages*. I can only + guess this is because PowerDNS can't generate these records? I *have no + clue*. Any useful information will be gladly accepted. I choose to ignore it. + + NSEC3 proving non-existence of l2v1y.7t5is.uvokchee.de/A: No RRSIG covering the RRset was returned in the response. See RFC 4035, Sec. 3.1.1. (216.218.130.2, 216.218.131.2, 216.218.132.2, 2001:470:100::2, 2001:470:200::2, 2001:470:300::2, UDP_-_EDNS0_4096_D_KN) + NSEC3 proving non-existence of uvokchee.de/CNAME: No RRSIG covering the RRset was returned in the response. See RFC 4035, Sec. 3.1.1. (216.218.130.2, 216.218.131.2, 216.218.132.2, 2001:470:100::2, 2001:470:200::2, 2001:470:300::2, UDP_-_EDNS0_4096_D_KN) + + As of 2015-01-11, I read the [PowerDNS + docs](https://doc.powerdns.com/authoritative/dnssec/migration.html#from-existing-dnssec-non-powerdns-setups-pre-signed) + again. Specifically, I need to set `pdnsutil set-nsec3 $zone <whatever + NSEC3PARAM says>`. Then, PowerDNS gives back SERVFAILs, because, of course, + PowerDNS can't sign the reply, because it doesn't have the keys to sign the + NSEC3 replies (??? I guess ???). So now, instead of sending back an unsigned + reply, it sends back an error. + + I imported the RRSIGs for these NSEC3 records, though, at least in a second + attempt. I tried all combinations of `(set-nsec3|unset-nsec3)` and `(import + NSEC3-RRSIG|don't import NSEC3-RRSIG)`. All variants failed. I have no clue + how this is supposed to work cleanly. [^7] + + **Update 2025-01-15**: The GitHub issue linked below (#9263) actually + contains a "solution"/workaround for this. The order of commands needs to be + 1) Import, 2) set-nsec3, 3) rectify, 4) set-presigned. + +1. Wait at least 24 hours (TTLs, DNS propagation time). +1. Let PowerDNS output its own keys it generated for the zone. Unfortunately, + `pdnsutil export-zone-dnskey $zone $keynr` *does not output a completely + valid record*, nor does `pdnsutil export-zone-ds $zone`. These outputs are + missing the TTLs in the second column, at least with PowerDNS 4.7.3 in the + Debian stable repos. You have to add those yourself. I saw some tools like + dnsviz break when you enter the records as-is. + + **Important**, I had to temporarily run `unset-presigned $zone` (see + below) before running `pdnsutil export-zone-ds`, so PowerDNS actually outputs + the hash of the new key(s)! Otherwise it will only show the current keys + signature. Otherwise, you may also use online tools that convert the DNSKEY + to a DS record. +1. Have a copy of the *current* DS / DNSKEY records as well (`dig` is your + friend). +1. Set the DNSSEC from "auto" to "manual" in the INWX web interface. + * Delete all keys from the domain. + * Add DNSSEC again for the domain, in manual mode. + * Add DNSKEY and DS records of the old keys. + * Add key, insert DNSKEY and DS records emitted by pdnsutil for the new + key. + + As far as I know, this will be sent to the parent zone. [^8] +1. After I got an email from INWX confirming the new DNSSEC entries, I ran + dnsviz again and nearly got an heart attack, because there were a lot of + errors and red exclamation marks. Actually, the DNSSEC was still valid (i.e. + not returning bogus records). The tool only complained about + + The DS RRset for the zone included algorithm 13 (ECDSAP256SHA256), but no + RRSIG with algorithm 13 covering the RRset was returned in the response. + + I *think* dnsviz expects both `RRSIG`s, i.e. both keys must sign the replies? + That shouldn't have an effect on the reachability, otherwise the tool would + report BOGUS records? + + **Update 2025-01-15**: Yep. As stated in the IETF document linked in the + references: + + > Current reading is that an algorithm rollover requires a full validation + > with all algorithms involved, whereas a key rollover will work whenever + > data can be validated using either key ([RFC4035], section 2.2). + + N.B.: So if you *really* want to avoid that, you need to tell PowerDNS to + create an KSK/ZSK pair (with the same parameters?) and use these, and only + later switch over to algorithm 13. +1. Wait at least 24 hours (TTLs, DNS propagation time). - Depending on the + previous DS records TTL. +1. Switch to automatic signing by PowerDNS. I guess at this point you must or should + * stop PowerDNS, [^5] + * `pdnsutil unset-presigned $zone`, + * `pdnsutil unset-nsec3 $zone`, + * edit the zone (clearing out the RRSIGs you imported. If I understood + the PowerDNS docs correctly, there will be trouble [^6] if you don't. Oh, + don't forget the NSEC3PARAM record, any leftover (C)DNSKEYS and (C)DS, + while also increasing the serial (otherwise the AXFR might not take + place), [^9] + * `pdnsutil rectify-zone $zone` + * start PowerDNS, + * (optional) notify the secondaries +1. At this point, you should be done. And I *guess* at this point you could + already delete the other DS/DNSKEY via the registrar? + +By the way, I'll choose to use NSEC instead of NSEC3. NSEC3 seems like too much +of a headache for me, also, domain names are not secrets. + +## Further references + +* [PowerDNS docs](https://doc.powerdns.com/authoritative/) +* IETF Draft: [Changing DNS Operators for DNSSEC signed + Zones](https://datatracker.ietf.org/doc/html/draft-koch-dnsop-dnssec-operator-change-06) +* [DNSSEC visualizer](https://dnsviz.net/) +* [Verisign Labs DNSSEC debugger](https://dnssec-debugger.verisignlabs.com/) + +## Footnotes + +[^1]: Okay, it's not like I edit my records that often. + +[^2]: + For the purposes of this blog article, I think you can freely substitute + zone with domain in your head, I probably won't use the words correctly 100% of + the time either. + +[^4]: + I think that shouldn't to any damage. DNS recursion should always ask the parent + zone? + +[^5]: + Avoiding a spurious notify or AXFR directly after editing? No idea if needed. + +[^6]: such as duplicate RRSIG replies. + +[^7]: + There are two GitHub issues similar to this: + [#9263](https://github.com/PowerDNS/pdns/issues/9263) and + [#8892](https://github.com/PowerDNS/pdns/issues/8892). + +[^8]: + Actually, I have no idea why INWX wants me to enter both the DS and the + DNSKEY. Only the DS gets entered in the DENIC servers. + +[^9]: + e.g. `:g/\<\(RRSIG\|NSEC3PARAM\|DS\|CDS\|DNSKEY\|CDNSKEY\)\>/d` in vim. +<!-- vim: set ft=markdown tw=80 ai tabstop=4 shiftwidth=4 expandtab: --> + diff --git a/_posts/2025-02-02-dn42-put-it-in-a-box-linux-network-namespace.md b/_posts/2025-02-02-dn42-put-it-in-a-box-linux-network-namespace.md new file mode 100644 index 0000000..3a43f1a --- /dev/null +++ b/_posts/2025-02-02-dn42-put-it-in-a-box-linux-network-namespace.md @@ -0,0 +1,134 @@ +--- +layout: post +title: 'DN42: Put it in a box (Linux network namespace)' +date: 2025-02-02 17:10 +0100 +last_modified_at: 2025-06-18 19:12 +0200 +lang: "en" +categories: "tech" +description: "I explain how I put my Autonomous System in a network namespace." +--- + +What did I do the previous week? What robbed me of my sleep at night, keeping my +thoughts churning? Let's look at "doing containers the hard way". + +For some time, I had CPU usage problems on my VPS. Looking at `htop`, I always +saw two bird instances and dnsmasq as "offenders". (I run both my clearnet AS as +well as my DN42 AS on this box) [^1]. I was originally going to write a blog article +about that, but it's still in my drafts folder. Here's the gist: + +- All these processes receive "netlink messages". +- Probably the IBGP session for my AS generates lots of these netlink messages. +- The other bird process (for DN42) and dnsmasq suffer from it. + +One possible solution is to put the processes into a container (Docker, Podman, +LXC, LXD, Incus, …). However, I'm on a budget. I have only 40 GB of storage on +my Hetzner VPS and don't want to waste it with duplicate file systems. However, I +can use the *technology* these container (runtimes/engines) use: Linux +namespaces. + +I won't cover the basics here. There are other blog articles from other people +who are *far better* at explaining that (e.g. from +[anracon](https://linux-blog.anracom.com/2017/10/30/fun-with-veth-devices-linux-bridges-and-vlans-in-unnamed-linux-network-namespaces-i/)). + +Suffice to say, I can put DN42 in a box, which put the network in isolation. To +a degree. I still need to communicate with the outside world. I dumped my setup +[in a git repo](https://git.uvok.de/ansible/tree/roles/linux-ns/files). + +[jamesits](https://github.com/Jamesits/systemd-named-netns) provides some nice +templates for setting up a network namespace. I used that template, but tweaked +some parts to they suit me better [^2]. Also, using the Debian systemd files, I +manually created new ones and made sure the processes use the separate namespace. +I admit to never having particularly liked systemd, but at least the service +manager is pretty nice. + +I also felt pretty clever coming up with [this setup +script](https://git.uvok.de/ansible/tree/roles/linux-ns/files/usrlocalbin/dn42-route-namespace.sh) +which gets called by systemd and then calls itself again, but in the newly created +namespace. + +Inside the namespace run: + +- The Wireguard interfaces to my peers, +- Tinc (which I only have because I want to have a broadcast-capable VPN), +- PowerDNS (a separate instance from "the outer VPS one", serving my DN42 domain), +- BIRD2, +- And a looking glass + +*Outside* the namespace run: + +- dnsmasq, which allows me to resolve my DN42 domains "from the clearnet" + (from within a Wireguard net) +- Nginx, which serves my DN42 website + +**Update 2025-06-18**: nginx now runs inside the namespace as well. + +It took me a while and some internet searches to come up with the firewall +rules. On my VPS itself I use ufw, for the network namespace, I *could probably* +make this work as well, but I decided to use "iptables", or rather, the wrapper +scripts which provide the same syntax but use nftables in the background. This +is because with this namespace separation, I don't have to worry about +"cross-leaking" network traffic between DN42 and the clearnet. So the rules get +a lot simpler + +I was happy that both DNS and the website work, when I realized that the default +policy for FORWARD was ALLOW. I found it suitable to set it to DROP, and +suddenly, it didn't work anymore, because I was employing destination NAT: + +``` +*nat +-A PREROUTING -d fd3e:bc05:2d6::80/128 -p tcp --dport 80 -j DNAT --to-destination fcee::1 +-A PREROUTING -d fd3e:bc05:2d6::80/128 -p tcp --dport 443 -j DNAT --to-destination fcee::1 +``` + +This is because the webserver is running on the "outer" VPS, not in the network +namespace (hey, it took me long enough to finish this up as it is). This is +probably a relatively small adjustment. + +With an additional forward rule, everything is happy again: + +``` +*filter +-A FORWARD -s fd00::/8 -d fcee::1/128 -j ACCEPT +-A FORWARD -s fcee::1/128 -d fd00::/8 -j ACCEPT +``` + +**Update 2025-06-18**: I modified this several times since then. +Since I also need to take care of actual routing/forwarding within DN42, +I now ended up with + +``` +-A FORWARD -s fd00::/8 -d fd00::/8 -j ACCEPT +-A FORWARD -i eth0 -d fd00::/8 -j ACCEPT +-A FORWARD -m conntrack --ctstate ESTABLISHED,RELATED -j ACCEPT +``` + +i.e. I don't rely on the source address being fcee::1 anymore. + +Also, I also feel pretty clever for making sure I can access DN42 from my +clearnet: + +``` +*mangle +-A PREROUTING -i eth0 -j MARK --set-mark 0x4242 +COMMIT + +*nat +-A POSTROUTING -d fd00::/8 -m mark --mark 0x4242 -j MASQUERADE +COMMIT +``` + +I am actually not sure if the latter needs an "-i (all wg interfaces)" or "! -i +(internal interfaces)" to avoid unnecessary NATting for when I access a service +in the namespace. But nevertheless, I achieved a working state. Best of all, I +can reuse some of the work if I ever want to put my clearnet AS in a namespace, +too. + +[^1]: + An AS is in ["autonomous system"]({% post_url + 2023-08-18-networking-adventure-my-own-ipv6-prefix-and-as %}), [DN42]({% link + dn42.md %}) is a "lab environment" for networking. + +[^2]: + For example, I have no idea why they unmount and mount the netns path + manually. Probably this fixes some bug of an old systemd version? + diff --git a/_posts/2025-03-06-monitoring-with-uptime-kuma.md b/_posts/2025-03-06-monitoring-with-uptime-kuma.md new file mode 100644 index 0000000..0d1a6d1 --- /dev/null +++ b/_posts/2025-03-06-monitoring-with-uptime-kuma.md @@ -0,0 +1,49 @@ +--- +layout: post +title: Monitoring with Uptime Kuma +date: 2025-03-06 18:55 +0100 +lang: en +description: "A short praise for Uptime Kuma, offering uptime monitoring." +--- + +[Recently](https://furry.engineer/@uvok/114026509150081909), I wanted to do add +some kind of monitoring to my servers. The prevalent reason was monitoring my +AS, which I accidentally broke by shutting down one server, or the hosting +provider had an outage (This was because I didn't configure a fallback default +route, but that's another story). + +So, I took a look at the monitoring landscape. And immediately wanted to drop +the idea again, because there were too many choices. And had no intention to +install and test them all, and no energy to read dozens of websites with user +reports. + +But then I said, "wait. Let's not do it the overthinking way again". So I took +the first best/simple thing and chose [Uptime +Kuma](https://github.com/louislam/uptime-kuma). I actually wanted to drop it +right away once I saw it's running on NodeJS (ehhh). But then I decided to spin +up an LXC on my Proxmox anyway. + +And lo and behold, it works: + +{% image +img="https://pics.uvokchee.de/_data/i/upload/2025/03/06/20250306175521-4763fdf7-me.png" +alt="Screenshot of Uptime Kuma - showing the ping times of various servers." +%} + +And it even has a certificate validity check. + +{% image +img="https://pics.uvokchee.de/_data/i/upload/2025/03/06/20250306175521-7805c0bb-me.png" +alt="Screenshot of Uptime Kuma - showing the HTTPS monitor, including the +remaining certificate validity time." +%} + + +It runs in my home network, so I can actually detect whether my AS is reachable +(to a degree). And it brings various notification options, from which I chose +Telegram and Matrix. + +I actually got an outage notification this week, on my Hetzner servers. No idea +what happened there, though, I didn't receive an outage report / notification +from them. + diff --git a/_posts/2025-03-18-games-i-play_ed.md b/_posts/2025-03-18-games-i-play_ed.md new file mode 100644 index 0000000..9e2c805 --- /dev/null +++ b/_posts/2025-03-18-games-i-play_ed.md @@ -0,0 +1,112 @@ +--- +layout: post +title: Computer games I (used to) play +lang: en +categories: game +date: 2025-03-18 10:17 +0100 +description: "I muse over computer games I played recently(-ish)." +--- + +I'm not big on computer games. Usually "I don't have the time" to deal with +them. Or rather, spending so much time on the computer at work, I'm quickly fed +up with sitting on the computer. Also, I get frustrated quickly at times, when +I can't make progress or repeatedly fail. So I usually only play computer games +on vacation. + +So, as for games I played (recently-ish)? Roughly sorted by time last played +ascending: + +- Waaaaaaaaaaaaaaay back in my childhood (in no specific order): + - [Civilization](https://archive.org/details/msdos_sid_meier_civilization) + [^civ1], [^civ2]. Yes, the original one! If I remember correctly, I always + got destroyed sooner or later… - [FreeCiv](https://www.freeciv.org/) is an + open source game inspired by it. + - [3D Pinball Space Cadet](https://alula.github.io/SpaceCadetPinball/). I + spent hours on that one. Never quite succeeding on hitting the targets… + - Anno 1602. I think the first game I searched for cheats to improve my + chances… - [Unknown Horizons](https://unknown-horizons.org) is a similar + game in open source. [^unkhor] + - SimCity 2000 [^simcit] - + [LinCity-NG](https://github.com/lincity-ng/lincity-ng) is a similar open + source game. + - Need For Speed III + - Empire Earth (quite like Age Of Empires, as I found out later) - As far as + open source goes, [0 A.D.](https://play0ad.com/) is probably the closest? + - "Die Völker" (apparently, "Alien Nations" in English, "The Nations" was + actually the sequel. Yeah, what?). I sunk quite some time into that one as + well. + - "Funk-Flitzer", which was on a "Mickey Maus" comic magazine. Go search for + "3-D Ultra Radio Control Racers". + - Worms 2 - [Hedgewars](http://www.hedgewars.org/) seems to be the open source + alternative. + - Moorhuhn, Winter Edition +- Sometime later deep in the past: Minecraft (I stopped way before Microsoft + acquired it), recently followed by [Minetest, or rather, + Luanti](https://www.luanti.org/) (Though, "it's just not the same anymore". + I'm not sure what exactly it is, maybe my changed mindset, maybe I liked the + original soundtrack and game elements more…). +- [Starbound](https://playstarbound.com/), very shortly +- [OpenTTD](https://www.openttd.org/): Trains and buses! Though, admittedly, I + never quite "got it" (why do you have to manually "park" passengers on train + stations, instead of unloading them completely, so they continue taking the + train?) +- [Dwarf Fortress](https://www.bay12games.com/dwarves/). Go with + [LNP](https://dwarffortresswiki.org/index.php/Utility:Lazy_Newb_Pack) if you + wanna give it a try, or the Steam version. +- [Stardew Valley](https://www.stardewvalley.net/) (on Android tablet) +- [Factorio](https://www.factorio.com/) - Shaking my head over the people + arguing over how to perfectly optimize everything ;). I disabled biters in + recent play-throughs, it got to annoying for me. +- [Terraria](https://terraria.org/). Another one where I had to resort to the + Wiki for the bosses. +- [Cattails: Wildwood Story](https://cattailsgame.com/). Got through the main + story, had to resort to YouTube for looking up how to beat the final boss. +- [Turing Complete](https://turingcomplete.game/) +- And, the most recent one, + [dotAge](https://www.michelepirovano.com/dotage.html) + +The latter [^dotnote1] one is a "turn-based village builder", with challenges. I +*guess* I can *kinda* compare it to Dwarf Fortress, as in, it can be incredibly +hard, and you have to build a civilization [^dotdwarf] and take care of it, as +in terms of food and drink, for example. Only you don't have to deal with goblin +or forgotten beast invasion, but, basically, nature. And DF doesn't have tech +research… Okay, maybe they're not comparable after all. + +The first play-throughs are rather rough, since you will only unlock additional +content, such as farming, with play time. So your first villages will cease to +exist quite quickly, I think. That's expected. Probably to show you the failure +modes? + +From personal experience: Don't build some new buildings too quickly. The game +allows you to build them even though they're "useless" at that specific point in +the game, and you need additional tech research to make them usable. + +{% linked_image +img="https://pics.uvokchee.de/_data/i/upload/2025/03/17/20250317185230-40c102c2-me.jpg" +url="https://pics.uvokchee.de/upload/2025/03/17/20250317185230-40c102c2.jpg" +alt="Screenshot of the game dotAge, of fairly early game play." +%} + +[^dotnote1]: + Yes, kinda unfair I only go into detail into one. I wanted to start + "reviewing" only this one, but then thought, "well, might as well list all + games I played so far". Maybe that's a chance for future blog posts. + +[^simcit]: + I didn't like SimCity 3000 as much. And *don't get me started with Cities: + Skylines*. + +[^dotdwarf]: + General advice seems to be not to go over 50 in dotAge. In Dwarf Fortress, + you have to deal with the pesky Nobles instead. Something similar seems to + exist in dotAge as well? + +[^civ1]: Go drop archive.org a small donation, won't you? + +[^civ2]: You can actually still play it thanks to [DOSBox](https://www.dosbox.com/) + +[^unkhor]: + Not sure about the current state. The port to the Godot + engine seems still to be a WIP. Last blog post is quite some time ago, but + the [GitHub repo](https://github.com/unknown-horizons/godot-port) is active. + diff --git a/_posts/2025-04-05-random-thought-smartphones-with-old-technology.md b/_posts/2025-04-05-random-thought-smartphones-with-old-technology.md new file mode 100644 index 0000000..4649817 --- /dev/null +++ b/_posts/2025-04-05-random-thought-smartphones-with-old-technology.md @@ -0,0 +1,20 @@ +--- +layout: post +title: 'Random Thought: Smartphones with old technology' +date: 2025-04-05 20:23 +0200 +lang: en +categories: tech +--- + +How would smartphones look with old technology? What if we never invented flash +storage? (Leave aside the answer "the smartphone would not have been +possible"). Like, what if they were using tapes / tape drives as primary +storage? Or floppy disks? + +<insert AI generated image here - hah, you wish. I'll have none of that on my +blog.> + +This thought was presented to me while listening to the ["Stay +Forever"](https://www.stayforever.de/) podcast, a German-language podcasts about +old games and their technology. + diff --git a/_posts/2025-04-06-i-don-t-get-kubernetes.md b/_posts/2025-04-06-i-don-t-get-kubernetes.md new file mode 100644 index 0000000..28224b4 --- /dev/null +++ b/_posts/2025-04-06-i-don-t-get-kubernetes.md @@ -0,0 +1,38 @@ +--- +layout: post +title: I don't get Kubernetes +date: 2025-04-06 15:59 +0200 +categories: tech +lang: en +--- + +No real content, just me ranting. + +There are [some ;)](https://xeiaso.net/talks/2025/surreal-joy-homelab/) who take +great joy in Kubernetes. I never really understood how I could use it. + +Okay, so, very simplified, K8s let's you say "I wanna run these services (Docker +containers) on my cluster (various computers/servers), optionally with +redundancy"? Well, I only have one "server" in my "homelab", and then 3 VPS or +so. Only one of them runs something in Docker/Podman. + +I *can't imagine*/don't understand how I would run, say, Nextcloud in K8s. I +*want* to know which server is currently running it, and where the data is +stored. Especially with something like Nextcloud, I want to have the Nextcloud +application, the database, and the data store on **one** VPS, without any +indirections, without any communication over the internet or a VPN, via some +proxy software. From what little I've heard about K8s (forgive me my ignorance), +I had more questions that I could answer. K8s seems really complex, because it +~~has~~ can have so many moving parts (yes, you can probably run a very basic +setup, most of the components seem optional). I don't want my database suddenly +moved around to somewhere else. + +That is to say: I never had a use case of trying out K8s. No *actual, real* one. +I could probably construct one if I tried really hard. But, eh. "My current +setup works". + +My attempt to run K8s on my Proxmox via LXC all failed, even if they're +privileged containers, probably because I need to mount Linux Namespaces, or +load specific kernel modules on Proxmox itself so they can be loaded in the LXC +containers as well (???). + diff --git a/_posts/2025-05-11-table-tennis.md b/_posts/2025-05-11-table-tennis.md new file mode 100644 index 0000000..8d9ce82 --- /dev/null +++ b/_posts/2025-05-11-table-tennis.md @@ -0,0 +1,14 @@ +--- +layout: post +title: Table Tennis! +date: 2025-05-11 08:16 +0200 +lang: en +categories: life +--- + +Recently, I was at a seminar. I learned a lot. It was an exquisite group of inquisitive people. +But we also had some free time in which we played some table tennis. +I have no idea how to play it besides "hit the ball with the racket". +Actually makes me want to join the local sports club for once, which does have a +table tennis department. + diff --git a/_posts/2025-05-25-cpu-usage-problems-again.md b/_posts/2025-05-25-cpu-usage-problems-again.md new file mode 100644 index 0000000..beb905a --- /dev/null +++ b/_posts/2025-05-25-cpu-usage-problems-again.md @@ -0,0 +1,16 @@ +--- +layout: post +title: CPU usage problems on my VPS again +date: 2025-05-25 19:29 +0200 +lang: en +categories: tech +--- + +<a href="{% post_url 2025-02-02-dn42-put-it-in-a-box-linux-network-namespace +%}">As reported previously</a>, I had problems with the CPU usage on my VPS +again, even after namespace isolation. This time, it was dnsmasq causing the +loadavg to rise. "This is a problem for future me to solve properly", is the +motto. For the time being, I simply added a service restart when I detect a high +loadavg. Works well enough. I'll keep monitoring it to see if this occurs more +than once a week or so. + diff --git a/_posts/2025-05-29-furdew-valley.md b/_posts/2025-05-29-furdew-valley.md new file mode 100644 index 0000000..cbdf420 --- /dev/null +++ b/_posts/2025-05-29-furdew-valley.md @@ -0,0 +1,24 @@ +--- +layout: post +title: Furdew Valley +date: 2025-05-29 15:21 +0200 +lang: en +categories: gaming +--- + +[In my last blog post]({% post_url 2025-03-18-games-i-play_ed %}) about gaming, +I think I already mentioned I played Stardew Valley. Back then, on an Android +tablet. Due to [Pan on Mastodon](https://woof.tech/@Pan_H_Shiroi@toot.cat) +streaming that game recently, I picked it up again. + +I found it can even be modded! The mod in question is +[Animals and Myths Pack](https://www.moddrop.com/stardew-valley/mods/1119098-fs-shs-animals-and-myths-pack). + +{% image + img="https://pics.uvokchee.de/upload/2025/05/29/20250529132445-6dbbe14d.jpg" + alt="Screenshot of modded Stardew Valley, showing the player character with anthro legs + and a fox tail" +%} + +That adds to the fun. I might even get a mod that adds NPC lines. The build-in +ones can get monotonous after some time. diff --git a/_posts/2025-06-16-oops-dn42-stops-working.md b/_posts/2025-06-16-oops-dn42-stops-working.md new file mode 100644 index 0000000..26d4ed7 --- /dev/null +++ b/_posts/2025-06-16-oops-dn42-stops-working.md @@ -0,0 +1,73 @@ +--- +layout: post +title: Oops, DN42 stopped working +date: 2025-06-16 20:39 +0200 +last_modified_at: 2025-06-17 18:12 +0200 +lang: en +categories: tech +--- + +As you might know, I participate in [DN42]({% link dn42.md %}). +I have a somewhat peculiar setup, in +which some VPS run the routing daemons, and my home router simply has a VPN +connection to them and statically routes everything `fd00::/8` to them. The router +runs OpenWRT, and has dnsmasq setup to resolve DN42 domains via the DN42 anycast +servers. I set this up *months ago*, it worked, I was happy, and didn't need it +since. + +Cue last weekend. "Suddenly" the resolution didn't work anymore. It simply timed +out. So I connected to my VPS (which is running DN42 +[in a namespace]({%post_url 2025-02-02-dn42-put-it-in-a-box-linux-network-namespace %})) +and took a look at tcpdump. Inside the namespace, I saw the strange lines + +``` +18:49:05.296629 eth0 In IP6 fd7a:115c:a1e0::xxx > fd42:d42:d42:53::1.53: 42631+ [1au] AAAA? wiki.dn42. (50) +18:49:05.296679 kioubit Out IP6 fd3e:bc05:2d6::80.50255 > fd42:d42:d42:53::1.53: 42631+ [1au] AAAA? wiki.dn42. (50) +18:49:05.302946 tinc_dn42 In IP6 fd42:d42:d42:53::1.53 > fd3e:bc05:2d6::80.50255: 42631 1/0/1 AAAA fd42:d42:d42:80::1 (66) +18:49:05.302990 kioubit Out IP6 fd3e:bc05:2d6::80 > fd42:d42:d42:53::1: ICMP6, destination unreachable, unreachable route fd3e:bc05:2d6::80, length 122 +``` + +And all the time I was thinking… "huh??? Why is `fd3e:bc05:2d6::80` unreachable??? +It is **clearly** in the `ip -6 a` output!!!". I looked through all the +iptables statistics and couldn't find the culprit. + +A join in the DN42 IRC and some back and forth later, someone suggested +"Hey, what's with the `fd7a:…` address? Is there a route for *that*?". + +And of course, no, it wasn't! I was so focused on the ICMP6 message that I +didn't notice the incoming line. As you can read in my other article linked +above, I perform NAT. Of course in that case it probably wouldn't make sense for the +ICMP6 message to tell someone that there's no route for the original IP (before NAT). + +**So, but… where does the `fd7a:…` address come from?**<br/> +The answer is [Tailscale]({% post_url 2024-12-08-trying-out-tailscale %}). +Unfortunately, they decided to use the `fd00::/8` IP range, which collides with DN42. +I didn't do any DN42 stuff since installing it, so I didn't notice that.<br/> +**But… why is that address used at all for the DNS request?**<br/> +Weeeeell… I found out as well. It comes from OpenWRT. I simply set up +a static route there, and Linux does its best to determine the source address for the +DNS request. And it seems the Tailscale one was a closer match than +the address from my own DN42 prefix.<br/> +**So, how to fix that?**<br/> +[It's not as easy as you think!](https://github.com/openwrt/openwrt/issues/13720). +Merely using the "source" option in the config file would work for IPv4, but +for IPv6 it has a different meaning!<br/> +**But why does it say "no route to host" instead of using a default route?**<br/> +Because I configured bird to insert an "unreachable" route for the `fd::/8` prefix +to avoid leaking traffic. +``` +# ip -6 route show fd00::/8 table dn42 +unreachable fd00::/8 dev lo proto bird src fd3e:bc05:2d6::1 metric 500 pref medium +``` + +At this point, it's Monday evening. Unnerved, I threw my hands in the air and +simply put a line of +``` +ip -6 route replace fd00::/8 ... src <my-openwrt-dn42-address> +``` +in `/etc/rc.local` and called it a day. My setup +works again, and I learned something again. Don't just look at the last line, +look at the whole picture. A lesson I actually already learned in the +ubuntuusers forums when asking for help compiling a package and only posted the +last few make output lines, which of course didn't contain the actual +compilation error… diff --git a/_posts/2025-06-22-blog-now-on-gemini-with-dn42.md b/_posts/2025-06-22-blog-now-on-gemini-with-dn42.md new file mode 100644 index 0000000..fa46a58 --- /dev/null +++ b/_posts/2025-06-22-blog-now-on-gemini-with-dn42.md @@ -0,0 +1,39 @@ +--- +layout: post +title: Blog now on Gemini - with DN42 +date: 2025-06-22 17:42 +0200 +--- + +The Gemini protocol is a minimal protocol to serve content, and is +the "spiritual successor" to the Gopher protocol. +(Do not confuse with Google's AI Gemini. I hate naming collissions), + +It took some tinkering, especially because Gemini's markup language +("Gemtext") +is deliberately +minimal, and Jekyll can't output/convert Markdown to Gemini, so I had to +take "the ugly route" to convert the "finished" Jekyll HTML page to Gemtext +via the below-mentioned tool, which basically does +HTML > Markdown > Gemtext. +I can't directly use the raw Markdown files of my blog, since I use +Liquid tags. + +Anyway, my blog is now accessible in "Geminispace", alas, only within DN42, +because I'm too lazy right now to do it properly. (With the DN42 namespace +isolation and all). And also, it's a really "nerdy" protocol, with I don't +know how many users. + +`gemini://uvok.dn42/` + +Addendum: What I really like is the "feed" specification, which basically consists +of separate lines of <br/> `=> $link $date $heading`, <br/> and browsers like +Lagrange can subscribe +to these (like RSS feeds, but the format is much simpler!). + +- [Gemini Protocol on Wikipedia](https://en.wikipedia.org/wiki/Gemini_(protocol)) +- [Gopher Protocol on Wikipedia](https://en.wikipedia.org/wiki/Gopher_(protocol)) +- [Gemini Protocol homepage](https://geminiprotocol.net/) +- [Gemini "Quickstart"](https://geminiquickst.art/) +- [Gemtext intro](https://gemini.flounder.online/docs/gemtext.gmi) +- [Html2Gemini](https://github.com/Aarontheissueguy/Html2GeminiPy) +- [Lagrange browser](https://git.skyjake.fi/gemini/lagrange) diff --git a/_posts/2025-07-30-awoostria-con-report.md b/_posts/2025-07-30-awoostria-con-report.md new file mode 100644 index 0000000..564e491 --- /dev/null +++ b/_posts/2025-07-30-awoostria-con-report.md @@ -0,0 +1,134 @@ +--- +layout: post +title: Awoostria Con Report +categories: furry +lang: en +date: 2025-07-30 19:16 +0200 +--- +It's time for another con report. I'm back from the second iteration of +[Awoostria](https://awoostria.at/), the Austrian furry convention in Vienna. + +## Day 0 / Wednesday + +As usual, more or less, I decided to go by train. It's only about 5 hours, anyway. +And I can sleep during the trip. Which I couldn't do if I went by car. + +Before the convention even started, I got into a Signal group with Tuxel, Nightraccoon and LynxOnRails. +From them, I knew that LynxOnRails was in the same train. We actually sat together for some time and talked a bit, before +I went back into my first class seat ;) to take a nap. + +Actually, I ran across another furry in the same train (easily recognizable, what other kind of person would wear a +tail and have a big fox plushie? ^^). That turned out to be NoteFox, which I should learn on the next day. +In the end, the train was only 5 minutes late. + +In the evening, I went eating with Tuxel, Nightraccoon, LynxOnRails to 5 Guys. +I wanted a BLT, which turned out to be a CLT (Charcoal-Lettuce-Tomato Sandwich). Meh. + +My three fellow furries played some rounds of Uno, but I had to go to bed early, so I couldn't play with. + +## Day 1 / Thursday + +The bed in the guesthouse I got was… meh. Might be because I have shoulder-neck issues anyway. +I booked the guesthouse without breakfast, because I wanted to save money. So I looked around and went +to get breakfast in an "eastern shop". It was a regular breakfast, bread rolls with jam and a far-too-hard-boiled egg. + +Since the con didn't really start yet, I went to the "Haus des Meeres" with Nightraccoon. +This is an aquatic animal exhibit. It is located in a former flak tower. +Actually, I'd have loved to visit the Zoo Schönbrunn, but that would've taken a whole day probably. +I need to remember to book a few extra days next year. + +{% image + img="https://pics.uvokchee.de/_data/i/upload/2025/07/30/20250730155904-e30e3043-me.jpg" + alt="Tower with aquarium." +%} + +Next to that was a computer gaming museum, which we didn't have the time/stamina to visit. + +{% image + img="https://pics.uvokchee.de/_data/i/upload/2025/07/30/20250730155904-346f7e81-me.jpg" + alt="Entrance to gaming museum." +%} + +In the evening, I enjoyed the CoVahr concert, and was really blown away to see fursuiters play +instruments. A truly special experience. + +{% image + img="https://pics.uvokchee.de/_data/i/upload/2025/07/30/20250730155904-c8160807-me.jpg" + alt="Stage of the concert, with CoVahr, Seishin, LightOfSolaris, NoteFox." +%} + +## Day 2 / Friday + +Went looking for breakfast again, and got desperate, because all cafés apparently only open at 9 a.m. or so, or even later. +In the end, I settled for a café, where the owners were coughing a lot, which made me feel very uncomfortable. +I sat outside, so it was probably okay. I got an omelette, which is not what I eat usually. +Also, a fucking wasp decided to visit me again, but this time I was prepared, I brought a spray bottle with water, +infused with lavender oil, which drove that insect away, so I could eat in peace. + +During the day, I met quite a few familiar faces, namely Ookami, Labwolf and Karpour. This made me quite happy. +(I was already overwhelmed by the crowded Wimberger lobby the day before, with lots of people I didn't know. +That stresses me out for some reason.) + +Also, I got to meet Kianga, which I only knew from online before. Yay! + +I even held a panel, the "Tinkering Show And Tell", which I already did at EAST last year. +We had leather masks, several electronic badges, moth wings with a quite sophisticated foldout mechanism, and +a very old VHS camera with some upgrades. I got some positive feedback for the panel in the end :). +Sadly, I missed the fursuit striptease charity event, which was happening at the same time :(. + +I got some food at the nearby "Loving Hut", which offered a special menu for furries even. +Sadly, it turned out that the Carbonara portion was way too much for me, so I had to forgo the cake. + +Then, in the evening, I attended the Riichi Mahjong panel held by Blujay and Viper. It was very nice to play +that game again after over 10 years. I think I last played it at one of the Berlicon conventions I went to. + +## Day 3 / Saturday + +As I got fed up looking for breakfast places, I simply went to get it at Flemings, since they has a superb +offer. One could attend the breakfast buffer for only 15 €. This had the added benefit I could enjoy breakfast in +company, with Nightraccoon, Tuxel and LynxOnRails. + +After breakfast, I got a nice massage from a learning physiotherapist. This was really needed. +That day was also the Whsprs concert which I enjoyed for a whole, before I decided to leave early to get +food at the lovely Maid Café the convention organized. It was in the Fleming's café/restaurant, +and fursuiters were roaming around serving the guests. That was lovely. +I also got a snep shirt in the dealers den later. + +I finally met Tabbie in person that day. I haven't seen him in suit during the whole convention, probably as +I was more around at Flemings. Also, I met Fox and Gustl that day. + +Also, during the days, I participated for a bit in the game that was prepared for the convention. +It had "reality" elements, but also had online elements. For the theme, they had the con space +nicely decorated. + +{% image + img="https://pics.uvokchee.de/_data/i/upload/2025/07/30/20250730155905-20137def-me.jpg" + alt="Table with various scientific equipment." +%} + +## Day 4 / Sunday + +I got breakfast at Flemings again, in nice company; later, I had lunch with Kianga and Keeya; +and in the evening, I had dinner with Fox and Gustl. CoVahr played the piano in the hotel lobby that day. + +Sadly, I didn't win any bids in the art show :( But I got a mail saying I won the lottery at GLC, though :). + +After the closing, I actually met Runo shortly, whom I haven't met in real life before, either. + +In the evening. I played some last rounds of Mahjong with Blujay, Perrydotto, Sylpheon and Sharky, +before we had to leave because the bar was closing. + +## Monday + +I got some breakfast at bakery at West station (because I needed to buy some stuff there), said my goodbyes, +hoping I didn't forget anyone, before heading back to the Meidling station together with Nightraccoon, where we both +had a coffee, before parting ways. The trip back home was quite boring, though. + +## Summary + +It's been a while since I had so much to do, felt some FOMO. The first few days I "panicked" a bit in the hotels, +because there were so many people around I didn't know, even if they were furries. In these situations, it +helped me to retreat to the community room. It wasn't exactly quiet, but at least it wasn't crowded. +Also, the feeling subsided once I met a few familiar faces. + +Now what's left for me is to wait for GLC, and then for next years Awoostria. diff --git a/_posts/2025-08-10-building-an-epaper-badge.md b/_posts/2025-08-10-building-an-epaper-badge.md new file mode 100644 index 0000000..fb6adf6 --- /dev/null +++ b/_posts/2025-08-10-building-an-epaper-badge.md @@ -0,0 +1,235 @@ +--- +layout: post +title: Building an ePaper badge +lang: en +categories: tech +date: 2025-08-10 18:30 +0200 +last_modified_at: 2025-09-01 19:45 +0200 +--- +## Foreword + +Two weeks before [Awoostria]({% post_url 2025-07-30-awoostria-con-report %}): + +> Hey, I should build something for my Tinkering Projects Show And Tell panel! + +So it begins… The story how I built myself an ePaper badge. + +Actually, the story begins way earlier (unrelated, when I still had a physical +Raspberry Pi running stuff in my home network). I wanted to tinker around a bit +and bought myself a Waveshare ePaper. These are simple black-and-white displays +which maintain their content when the power switches off. They are also inside +eBook readers. + +This was also when I wanted to build myself an electronic door sign for the +EAST convention with these, and I wanted to go "as minimal as possible". I +wanted to use one of the MSP430 controllers I had laying around, and I wanted +to change motives via MiFare RFID transponders (using an MFRC5xx reader). Work +on that development never really took off. (Ugh, too little flash for all the +pictures, too much stuff to code myself!) + +## Requirements + +So this time, I simply said "fuck it", and threw an ESP32 on the problem. +Also, I decided to use [PlatformIO](https://platformio.org/), a +toolchain/SDK/library manager. I started with the Arduino framework, which is… +pretty wasteful in terms of resources (Flash, RAM, CPU etc.), but speeds up +development significantly. + +I had a simple ESP32 devboard, and one of the Waveshare modules, and started +coding. + +… + +But wait, what do I even want to achieve? Well, I wanted to "mood badge", i.e. +show my current mood with funny pictures. I couldn't get one on previous +conventions, so I was just gonna build one myself. + +This involves several sub-problems: + +* [Control the ePaper display](#control) +* [Get the pictures on the display](#pic) +* [Set what is displayed](#setdisp) +* [Power-saving](#powersave) +* [Attach the badge to myself](#attach) + +<span id="control"></span> +## Control the display + +Usually, you never talk to the displays themselves, but to a display +controller. You talk to these via a digital interface, e.g. SPI. There are +different display controllers with different command sets. + +But why bother with implementing this myself? There are ready-made libraries. +For myself, I decided to use [GxEPD2](https://github.com/ZinggJM/GxEPD2). They +support *some* Waveshare displays. The problem with Waveshare displays is, they +don't disclose which display controller they use. So it's kind of an +trial-or-error procedure. Or rather, you can look at their example code, figure +out which commands they are using, and compare what commands GxEPD2 uses. +That's a bit cumbersome. But still better than writing everything myself. Also, +it supports graphics primitives! + +<span id="pic"></span> +## Get the picture on the display + +You can't just simply throw a JPEG onto the display. The display doesn't +understand that. It only understands pixel data. Also, the display can only +draw black and white pixels. I also have a display with yellow color support, +but that makes it even more complicated, actually. Even when you don't use it, +refresh is slow. + +So, you definitely can't throw a color picture on the display, nor a monochrome +one. There are displays which support a few gray-levels, but I don't have one +of those. + +So. What to? The solution is "dithering". I.e. you trick your eye into +perceiving grey by having clusters of black and white pixels. There is some +technical background to dithering (see the Reference section), but I simply +used either GIMP with the Floyd-something algorithm, or one of the "ordered" +modes of ImageMagick. It was a bit of trial-and-error and +seeing-what-looks-best. + +The result, then, looks like this: + +<img + src="https://pics.uvokchee.de/upload/2025/09/01/20250901174428-eac9e946.jpg" + alt="a dithered image of my fursona" +/> + +Now, about the image format… GxEPD2 supports "XBitmaps", or XBMs, which are +basically just a C array declaration, so you can GCC that file and throw in the +array into the GxEPD2 function call. And voilá, it works. You need to set the +rotation first, though. + +<span id="attach"></span> +## How to attach the badge to myself + +I have a Waveshare module/PiHat (which is too heavy), and a simple "ePaper +sheet" including a plastic housing for it. The housing can only fit the ePaper, +not the devboard, though. Also, it would be too cumbersome to attach to the +devboard - loose wires! So, at this point, I decided to switch from the +prototyping platform onto something better. + +Fortunately, Elecrow provides a +[CrowPanel](https://www.elecrow.com/wiki/CrowPanel_ESP32_E-paper_2.9-inch_HMI_Display.html), +which is exactly what I need. It has a display, a built-in ESP32 controller, a +housing, and even some switches! As a huge plus, they even specify which +display controller they use. I had to try some of the GxEPD2 display classes, +but finally found one working. + +I decided to glue magnets onto the housing, and attach the display via magnets +on the inner side of my shirt — not ideal. I positioned the magnets in +the (vertical) middle of the housing, so it wobbles and is not readable. Also, +I accidentally washed the shirt after Awoostria with the magnets still sticking +inside — and now there's a hole in it :( . This problem is still +unsolved. I can kinda attach the magnets to the housing screws at the top, but +that's not *very* stable. + +When starting to work with the Elecrow display, at first nothing would work. +When I looked at their example code I noticed there's an additional power pin +that needs to be toggled. + +<span id="setdisp"></span> +## Set what is displayed + +In addition to these switches, which allow choosing the motive, I wanted +something "more direct", so I added the +[NimBLE-Arduino](https://github.com/h2zero/NimBLE-Arduino) library. With a bit +of coding, I added a service and some characteristics, so the available motives +could be read via BLE. Also, the motive could be selected via another +characteristic. I started writing the characteristic with *nRF Connect For +Mobile*, but started writing an app [later](#theapp). + +Actually, the switch-selection was a bit troublesome. Redrawing the whole +display takes around 2 seconds — but that is not acceptable when +navigating the presets one-by-one. By looking at the API, I found out you can +select a "partial region". + +What I didn't mention yet, the text that shows the mood is drawn at runtime, +not integrated into the picture. So, I simply update a region in the +vertical-center-right of the display with the mood text. The picture stays the +same, but the text reflects the selected mood. The selection is confirmed my +pressing the rotary switch. + +This is still not ideal. The first update after power-up must be a full one, +and I don't save the selected preset in NVS — I don't want to destroy the +flash by lots of write cycles. I don't have a solution to this, yet. Maybe I'm +gonna integrate an microSD card (there's a slot for that in the CrowPanel). +I'm gonna research a good wear-levelling file system for that. Probably not +FAT. That doesn't need to be readable on the PC. (And even if, simple stuff +can be written in FUSE). Alternatively, drawing the first motive on power-up +would also be an option, but I don't like it that much. + +<span id="powersave"></span> +## Power saving + +I first measured the current and was shocked. The whole thing draws around +80-100 mA. Not a big surprise, given that Arduino basically calls `loop()` over +and over again. + +Using a bit of experimenting, and failing to cancel light sleep with a GPIO +interrupt, I implemented power saving by using a timer-based light sleep (10 +ms, gives good user response) and reducing the CPU frequency to 80 MHz. And lo +and behold, my USB current measuring equipment (resolution 10mA) showed 0 mA. +Success. + +Actually, reducing the CPU frequency was a requirement! If I didn't do that, +the CPU would constantly crash when entering or exiting light sleep. No idea +why! + +Apropos of powering: The badge is normally unpowered and only powered if I need +to change the motive. I don't want to have an USB cable hanging on me the whole +time! Using a battery might be an option, but I had problems with mismatched +connectors — the Elecrow display doesn't have a standard JST connector +like the LiPo battery I bought (Li-Ion might even be the safer option? I have +no clue about this stuff. With a quick search, I only found these cylindrical +Li-Ion batteries and have no idea how I would connect them). The badge seems to +have a "mini" variant of that connector. + +For the time being, I power it with a USB power bank, but this I still consider +an unsolved problem. + +<span id="theapp"></span> +## The app + +Writing the BLE characteristics with nRF Connect is all and well, but not +really user-friendly. I didn't want to install the Android SDK, so I looked at +cloud based development for a start. I found [MIT +AppInventor](https://appinventor.mit.edu/). First, I was disgusted, because +apparently they require Login with Google. But I found [an alternative +way](https://code2.appinventor.mit.edu/) by which you simply get a +"Passphrase-like" codeword you use for login. + +The graphical programming is unusual to me. I used Scratch shortly in the past, +so it was not completely foreign. Actually, it was kinda fun coding this, in +"event style", once I figured out how to to like stripping, list filtering, +etc. + +<img + src='https://pics.uvokchee.de/upload/2025/09/01/20250901174428-91da9ca4.gif' + alt='Screenshot of AppInventor showing part of the program.' /> + +This was good enough for a while, but then I decided I wanted to actually have +the source code available. So I looked again at development options, and +settled for Flutter. + +Again, this was completely new to me. I started off with a popular BLE library, +which turned out to be an unfortunate choice, as Linux support had a few +quirks. That was probably a good thing in hindsight, as this made me abstract +away the BLE stuff in implementation classes, so I could easily try out +different libraries, and only use the abstract base classes in the code. Well, +you can see what the code looks like, I linked my repo below. This is what the +motive selection looks like: + +<img + src='https://pics.uvokchee.de/upload/2025/09/01/20250901174428-f3f0d032.gif' + alt="Screenshot of the Flutter app, allowing selection from + sleepy, hungry, hugs?, uvok, overstim, contact, games?" +/> + +## Resources + +- [surma.dev about dithering](https://surma.dev/things/ditherpunk/) +- [git repo with badge source code](https://git.uvok.de/espadge/) +- [git repo with app source code](https://git.uvok.de/espadge-flutter/) + + diff --git a/_posts/2025-09-04-activating-csp-for-my-blog.md b/_posts/2025-09-04-activating-csp-for-my-blog.md new file mode 100644 index 0000000..49a985b --- /dev/null +++ b/_posts/2025-09-04-activating-csp-for-my-blog.md @@ -0,0 +1,27 @@ +--- +layout: post +title: Activating CSP for my blog +date: 2025-09-03 19:29 +0200 +lang: en +categories: tech +--- + +Recently, I stumbled across a [media.ccc.de](https://media.ccc.de/) talk about [internal.nl](https://internet.nl/). +Basically, this is a website that tests your website security. + +For me, it deducted points for missing HTTP headers. Amongst them, +[`Content-Security-Policy`](https://developer.mozilla.org/en-US/docs/Web/HTTP/Guides/CSP). +Basically, that header says what content may be loaded on the website. +Especially, it can prevent loading stuff from external sites. (Cross Site Scripting as attack scenario). + +So, basically, it doesn't add *much* value for my blog, since this is a static site and I control the content. +Sure, there is my comment system, but even that I consider safe enough to handle escaping. So +setting the header was mostly done to score fake internet points only. But also, a chance to learn something. + +Because, even after adding `self` and my domains to the respective header fields, some stuff would not work. +Mainly because of inline scripts and inline styles. So I put them in separate js files and created CSS classes. + +One thing that doesn't work anymore are avatars for the ActivityPub comments (and probably for the Isso comments?). +This is because I have no idea from what servers I will get comments. So, I replaced the avatars by a grey square. + +And that's it already, really. diff --git a/_posts/2025-09-10-installing-ca-certificates-on-android-also-16.md b/_posts/2025-09-10-installing-ca-certificates-on-android-also-16.md new file mode 100644 index 0000000..5c8cdd4 --- /dev/null +++ b/_posts/2025-09-10-installing-ca-certificates-on-android-also-16.md @@ -0,0 +1,17 @@ +--- +layout: post +title: Installing CA certificates on Android (also 16) +date: 2025-09-10 19:35 +0200 +lang: en +categories: tech +--- + +Are you tired of getting "Private key required to install a certificate" when trying to +install a CA certificate under Android via the settings app? +(It never works via the file browser directly. You have to go via, and I only paraphrase, as I only have GrapheneOS here, no LOS: +Settings > something security > (more privacy and security?) > something login data/credentials/encryption > Install a certificate) + +Just check + +- The certificate must be *in PEM format*. If it is in DER, you get the error above. +- The file extension must be `.crt` or `.cer`. Not `.pem`. Otherwise you get a different error. |