Tue, Nov 8th, 2022

Ish Sookun posted at 18:00

openSUSE Board Election 2022 campaign has begun

The candidates list for this year's openSUSE Board Election is as follows:

openSUSE members can also ask questions to the candidates on the project mailing list. Vojtěch Zeisek asked the candidates about their plans and what they want to achieve with the project.

Douglas had an interesting answer. He stated that he would like to see that the openSUSE Project adopts the blockchain technology. He cited the election as an example where a smart contract could facilitate the task of running elections and maintaining an updated members list based on whether members' tokens have been used in (x) number of years.

He also mentioned NFT as something that could be explored to create a sort of badge system like the Fedora project has and member contributions could be rewarded with NFTs.

On the question about what he wishes to do, he answered that he would focus on getting the project either becoming a Foundation or transition to a decentralised autonomous organisation. Discussions about creating an openSUSE Foundation started in 2019 but it hasn't progressed much since.

I will write more about the candidates Q&A with members as they happen. If you would like to ask a question or follow the discussions, then feel free to subscribe to the project's mailing list.

openSUSE site Aligns with Upstream Documentation

The history of documentation as it relates to operating systems and software development has a rich history that expands decades.

The founding of manual pages, or manpages for short, were a way to onboard new technology users at a time when household computers were nonexistent.

To gain knowledge of programs, standards, abstract concepts and conventions, a person needed computer access and to enter the man command to display documentation in a green text encoding standard about the computer program on the system.

Times and technology have changed, but the purpose of manpage hasn’t.

Users no longer need to install a package on their system to access a program’s documentation thanks to the openSUSE Project’s repository of manual pages at manpages.opensuse.org.

There are a couple of different ways to use the manpages repository. People can browse the repository index, which features thousands of packages (curently 111,387), enter the package in the search or enter the /name of the package in the URL.

The manpages repository follow upstream manual pages in openSUSE Factory and translations are based on these upstream translation efforts for each software package.

Service for manpages.opensuse.org will improve and updates to each of the packages manpage will happen as new packages enter openSUSE Factory.

A link will soon be displayed on the project’s portal to all of openSUSE websites, user groups, social media accounts and more.

Mon, Nov 7th, 2022

No more updates for nodejs14, below in Leap 15.4

As of today, nodejs14 as well as any older nodejs versions will no longer receive updates in openSUSE Leap 15.4.

Users are adviced to switch to nodejs16 instead. The nodejs16 version is an official package in Leap 15.4 despite software.opensuse.org not visibly showing the tag. There is a issue filed to fix that on the website.

Fri, Nov 4th, 2022

openSUSE Tumbleweed – Review of the week 2022/44

Dear Tumbleweed users and hackers,

Despite the week being one hour shorter (as a reminder: Europe switched from summer time to winter time on Oct 30), the maintainers and contributors went beyond and still delivered 7 snapshots (1028…1103). The staging projects have been nicely balanced and performance seems good. Unless the requests cause breakages, they are still going through the process rather quickly.

The 7 snapshots brought you updates in these area:

  • Mozilla Firefox 106.0.2 & 106.0.3 & Thunderbird 102.4.1
  • gpgme 1.18.0
  • Linux kernel 6.0.5 & 6.0.6
  • Python 3.10.8
  • Sudo 1.9.12
  • KDE Plasma 5.26.2
  • strace 6.0
  • btrfsprogs 6.0
  • GNOME 43.1 (gnome-shell, mutter and gnome-desktop did not get an update in this release, which is why gnome-control-center still reports 43.0)
  • openssl 1.1.1s & openssl 3.0.7

A lot of requests have been submitted in the last days and the staging projects are busy building and testing those changes. The most relevant are:

  • KDE Applications 22.08.3
  • CMake 3.24.2
  • Qt 5.15.7
  • Libvirt 8.9.0
  • SQLite 3.39.4
  • Linux kernel 6.0.7
  • GNU Make 4.4
  • git 2.38.1: breaks python-GitPython
  • icu 72.1: breaks nodejs18/nodejs19 (and a chain behind this)
  • suse-module-tools 16.0.24: breaks virtualbox and vmdk (and potentially more kmp builds)

Thu, Nov 3rd, 2022

LLVM, sudo, Plasma update in Tumbleweed

This week’s openSUSE Tumbleweed snapshots continued to roll forward and update more than 150 software packages.

Besides updates for LLVM, sudo and KDE’s Plasma, packages like systemd, curl, strace and tracker also gained software updates.

An update of gnome-terminal 3.46.3 arrived in snapshot 20221101. The package updated translations, put to use a new icon and removed XML namespaces. Other GNOME packages updated in the snapshot like document viewer evince 43.1. The document viewer fixes a crash and avoids a rendering issue. An update of glib2 2.74.1 had a patch that reverts the handling of collisions between standard input/output file descriptors and newly created ones, which solves the password and secrets storer gnome-keyring-daemon from eating 100 percent CPU. The building blocks package for libraries and applications written in C also fixes regression with int64, which is used to represent 64-bit signed integers; the package also fixes various build failures in different situations. Terminal Emulators vte 0.70.1 implemented the clipboard for GTK4, added a define for Apple’s darwin and fixed a filter for unwanted environment variables. Macedonian translations were added with an update to yast2-trans. A few other packages were updated in the snapshot.

The new major version of the diagnostic, debugging and instructional userspace package strace was made available in the 20221031 snapshot. The 6.0 version updates the decoding of setns system call, which allows for the calling thread to move into different namespaces, and updates the lists of ioctl commands related to Linux Kernel 6.0. The package update of timezone 2022f will let people reading this Tumbleweed blog know that Mexico no longer observes daylight savings except near the US border. Chihuahua moves to year-round time, but it’s unclear if that is for the state or the city. The timezone update changes the time for Fiji as it also no longer observes daylight savings. The few Python Package Index and RubyGems packages were updated in the snapshot as well.

Snapshot 20221030 was more of a RubyGems snapshot that anything else although it had two PyPI updates; python-zope.interface 5.5.0 and python-colorama 0.4.6. Some RubyGems like rubygem-openid_connect added two-way authentication mTLS access token capabilities in the 2.2.0 update. An update of rubygem-pg 1.4.4 reverted a change to let libpq do the host iteration while ensuring the parameter [connect_timeout](https://github.com/ged/ruby-pg/pull/485) is still respected. RubyGems application dependencies package rubygem-bundler fixes a User Interface issue when bundler duplicated gems; this was done by deduplicating the list. One of the few non-RubyGems packages to update in the snapshot was to the application and emulator filter luit 0221028, which updated a configuration script to work around regressions in grep 3.8.

Plasma 5.26.2 was updated in snapshot 20221029. KDE’s software center Discover makes sure to look up the correct resource for Flatpak and now shows the beta information for apps on the backend. Window manager and Wayland compositor KWin replaced some manual pointer conversions with calls and fixed a potential race condition when the text input state changes and when focus changes happen at the same time. Fixes to dragging desktop components were made with the plasma-desktop update and the package fixed font size changes when migrating from Plasma 5.25. A minor update of llvm15 15.0.3 adds a patch to fix the lowering of non-canonical vector comparisons on ARMv7. An updated of decoder mpg123 1.31.0 fixed an interaction of pause (looping) with buffer, adding a --pauseloop to set the loop interval. The package also added interruption handling to fix a bug for certain Advanced Linux Sound Architecture setups. Several other packages were updated in the snapshot.

Browser Mozilla Firefox 106.0.2 fixed a handful of bugs in snapshot 20221028. One of those fixes notifications in the sub-panel settings and another fixes the browser from freezing on some sites. The update of sudo 1.9.12 was extensive. It fixed a bug when logging the commands exit status in intercept mode. It also fixed a bug that prevented event log data from being sent to the log server when I/O logging is not enabled. Tracker and tracker-miners both updated to version 3.4.1. The searching and indexing functionality packages both had fixes for memory leaks. The latter improved performance lookups and provided new handling of syscalls. An update of the mobile remote terminal application mosh 1.4.0 added true color support and syslog logging of connections. The libstorage-ng 4.5.48 update set used feature flags and an update of Plymouth fixed some plugins and dropped a few patches. Linux kernel-source 6.0.5 update provides support GNU Compiler Collection 12.1 and newer compilers, and it had a firmware change that doesn’t free memory if an Advanced Configuration and Power Interface table is loaded successfully. Python updated in the snapshot; a fix for multiplying a list by an integer to detect an integer overflow when a new allocated length is close to the maximum size was made with the python310 3.10.8 update. Many other packages were updated in the snapshot including yast2-firstboot 4.5.5 and yast2-packager 4.5.6.

The 20221027 snapshot that came shortly after publishing last week’s blog had an enormous amount of updated packages. Three Common Vulnerabilities and Exposures were fixed with the curl 7.86.0 update; Daniel Stenberg provided a video from Oct. 26 providing feature changes and discussing pending removals that will be coming in the future. ImageMagick added a private Application Programming Interface to go through a linked list without using semaphores. Advanced Linux Sound Architecture 1.2.8 added a keyring and added support for pause/resume and for an ID3v2 tag skip. An update of systemd 251.7 added support for QR code encoding library libqrencode 3.0, and it reverted a system time set back that introduced regressions that affected many users. LibreOffice fixed a bug where queries don’t show any content when executed directly through the Graphical User Interface. The yast2 4.5.18 update improved logging in the product control module and uses the new log.group call to group logs for each workflow step. Other packages to update in the snapshot were GTK4, dbus-1 1.14.4, mtools 4.0.42, webkit2gtk3 2.38.1 and several more.

The continuous streak of Tumbleweed snapshots stands at 21.

Photography is not just about the camera

Once upon a time I started taking photos with a Lubitel, which is an old, very basic, and completely manual camera. In 2000 I switched from film to digital and everything could be automated. This was the time when I finally realized that having a good camera is not everything. A perfect exposure with a good camera can still result in an ugly and boring photo.

Lubitel 2

When I had a fully manual film camera, I quickly learned how to do perfectly exposed photos without any tools to measure light or distance. My later film cameras had exposure metering, but still, my own estimates were much better than the measurements of my cameras. I had some really nice photos, but most of them were pretty boring, despite being perfectly exposed. Knowing that I had some cheap, Soviet and DDR made cameras, I blamed it on the tech, of course. Yes, I blamed boring photos on the cheap cameras even though my exposures were 100% perfect, sometimes even better (with a bit of luck, one could take 37 photos on a 36 photos film).

My first digital camera was a Nikon Coolpix 950. This was state-of-the-art camera in 2000, way ahead of the competition. I did not have to guess exposure and distance anymore, as everything was properly measured and set by the camera. Still, the majority of my photos were ugly and boring. This was an eye-opening moment for me: I realized that technology is not everything.

For almost two decades, my primary focus was on mastering the perfect exposure and distance without any tools. This camera could set those on its own. This was the moment when I realized that composition is also key. Making sure that I focus on the main subject, do not chop off the head or legs of people, select a proper background, that I am aware of the depth of field and the rule of thirds, and so on.

To me, mastering the proper exposure was an instinct. Learning how to compose nice photos was a long learning process. I have some really nice photos. Most of them are now well composed, but there is nothing really special about them. No matter how many photos I take or how many books I read about photography, it is not really possible to learn creativity…

For many years I considered mobile photography a joke. Compared to a full frame or APS-C camera, the lens and sensor in a mobile are ridiculous. However, the camera is not everything. Of course, the camera can limit some of the advanced possibilities, but not the composition and creativity.

Learning how to use a camera can be overwhelming. A good camera is also expensive, but using “just” a mobile does not mean that someone is not good at photography. I met quite a few people who were bullied by people with expensive cameras that they suck at photography. And yet, when you look at their photos taken using their mobile, you see that they do wonderful compositions without ever hearing about the rule of thirds, or knowing about timing or aperture. With a bit of encouragement, they understood that they are taking nice photos and some even started to learn photography.

Long story short: a good camera can give a lot more flexibility and extra quality, but it is just one ingredient of good photos. Do not discourage anyone from pursuing photography just because they are using a mobile or a point and shoot camera.

You can find some of my photos on Gurushots.

Wed, Nov 2nd, 2022

Melhoria na infraestrutura de mirrors no Brasil e América do Sul

Segundo as estatísticas do projeto coletadas com Matomo (antigo Piwik), o Brasil está entre os cinco países que mais utilizam as distribuições do openSUSE.

O Brasil está em terceiro lugar na popularidade de uso do openSUSE, atrás apenas dos Estados Unidos e Alemanha. Possuir uma rede de réplicas, para levar downloads e atualizações de pacotes das nossas distribuições para os usuários do Brasil e América do Sul, é importante.

Graças a alguns membros do projeto, como Alexandre Vicenzi, Erico Mendonça, Ricardo Klein e outros, a velocidade e qualidade de entrega dos downloads do openSUSE melhorou significativamente.

Antes dos esforços para melhorar a qualidade da infraestrutura do Brasil, tinham-se poucos mirrors e a Universidade Federal do Paraná. O C3SL na UFPR é o maior mirror do hemisfério sul, mas como hospeda muitas distribuições Linux e outros projetos, não é o mais rápido.

Segundo Alexandre, “As atualizações do Tumbleweed eram sofridas, pois poucos mirrors da América do Sul mantinham ele atualizado, quando o possuíam”.

Como uma distro rolling release, as atualizações semanais trazem vários MBs ou até GBs em downloads para os usuários.

Alexandre comentou que colaboradores do openSUSE e a comunidade brasileira do openSUSE no Telegram se queixavam com frequência sobra a qualidade do download e atualizações das novas versões.

“Eu pensei, precisamos fazer algo. Muitos mirrors atualizam apenas a cada 6 horas, ou mais. Então é comum que muitos requests sejam redirecionados para a Europa. Isso adiciona latência indesejada e gera confusão.”, comentou Alexandre.

Além da comunidade, alguns clientes corporativos também reclamaram. Alguns repositórios do openSUSE são compartilhados, ou usados, por clientes da SUSE. Os problemas de infraestrutura não afetavam apenas a comunidade, mas também empresas e entidades que dependem do software que a comunidade cria e mantém.

Esses problemas motivaram colaboradores do openSUSE a entrar em contato e buscar o suporte de empresas e universidades.

“Alguns foram solícitos, alguns nunca responderam, outros mostraram interesse, mas infelizmente não possuíam espaço livre devido a hospedar outros projetos”, comentou Alexandre. “A primeira empresa a colaborar foi a Binario Cloud. Eles disponibilizaram um servidor com 1 TB de disco”.

Alexandre gerencia o mirror na Binario Cloud. O mirror contém Leap, Tumbleweed e é atualizado a cada 15 minutos. O mirror ainda conta com os repositórios do Packman.

A Universidade Federal do Mato Grosso também foi uma das universidades que colaborou.

“Eles disponibilizaram aproximadamente 300 GB, e eu ajudei a fazer a configuração do mirror”, comentou Alexandre.

Com a ajuda do Klein, os esforços inicias se multiplicaram. Com a sua ajuda, foi possível entrar em contato com a Edgium e a Locaweb. A Edgium disponibilizou uma VM para hospedar um MirrorCache e a Locaweb providenciou um mirror com 3 TB de espaço. O mirror da Locaweb ainda precisa de alguns ajustes, mas tem potencial para crescer no futuro.

A empresa mais recente a nos ajudar foi a Tyna Host.

Segundo Alexandre, “Eles nos forneceram três VMs e 1 TB de disco SSD”. Essas VMs estão sendo usadas para hospedar um mirror, um MirrorCache e um proxy cache.

O Erico Mendonça é responsável pelo domínio opensuse.net.br e a lojinha oficial do openSUSE Brasil. Além disso, ele é responsável por monitorar e avaliar a qualidade da infraestrutura no Brasil.

Tudo que a equipe do openSUSE Brasil hospeda pode ser encontrado em github.com/opensuse-brasil/ e o que a equipe tem conhecimento na América do Sul é monitorado em status.opensuse.net.br.

O projeto openSUSE gostaria de agradecer a todas as empresas, entidades e pessoas que ajudaram a melhorar a infraestrutura no Brasil e na América do Sul.

Entre em contato com a equipe brasileira pelo grupo openSUSE Brasil no Telegram.


Significant improvements in Brazilian and South American mirror infrastructure

Brazil is among the top five countries using openSUSE distributions, according to the project’s open source web analytics instance Matomo (formerly known as Piwik).

Trailing just behind the US and Germany, Brazil takes the third position according to the popularity of use. Having a replica network bringing users in South America downloads and package updates of the distributions is essential.

Thanks to some members of the project like Alexandre Vicenzi, Erico Mendonça, Ricardo Klein, and many more, the speeds for delivering openSUSE goodness on mirrors from download.opensuse.org have made significant improvement.

Before the efforts to improve the mirrors, Brazil had only had a few mirrors and the Federal University of Paraná. The C3SL at UFPR is the largest mirror in all of South America, but it wasn’t the fastest as many other projects use it as well.

Tumbleweed updates were terrible, as very few mirrors in South America had it and kept it in sync,” Vicenzi said.

The rolling release brings hundreds of MB of updated packages every week, so the throughput has people using Tumbleweed updating their distribution regularly with zypper dup command.

Vicenzi said some openSUSE contributors and the Brazilian openSUSE community in Telegram complained about the mirror quality in Brazil.

“I thought, we need to do something about it”, he said. “Many mirrors have a policy of a six-hour update or even higher. Thus, it was common to have many redirects outside South America to European countries. This added to the latency and misdirected traffic greatly.”

Even some corporate customers complained. Certain customers use community packages from openSUSE repositories so improving the mirrors affected not just community enthusiasts, but businesses that use community software.

This motivated the community to contact companies and universities to get support.

“Some were very supportive, some never replied, and some, while interested, had no infra left for us, as they were already full, hosting something else”, Vicenzi said. “The first and most supportive company was Binario Cloud. They provided us with a server and 1 TB storage.”

Vicenzi manages the Binario Cloud mirror for Leap and Tumbleweed; it updates every 15 minutes. The mirror even has Packman repositories now.

The Federal University of Mato Grosso was also one of the supportive universities.

“They provided us with ~300 GB, and I helped them set up everything”, he said.

With the help of Klein, the efforts paid off again. The group was able to get in touch with Edgium for another machine and Locaweb for another mirror. The Edgium machine hosts a MirrorCache and Locaweb provided a mirror with initially 3 TB, which still needs some adjustments, but has greater potential to grow in the future.

The most recent company to support the efforts was Tyna Host.

“They provided us with three VMs and about 1 TB”, Vicenzi said. These VMs are being use to host a mirror, MirrorCache and download content.

Mendonça has been taking care of the opensuse.net.br domain and the official openSUSE Brazil swag store. He is also running monitoring tools and evaluating the performance of the new infrastructure in Brazil.

Everything the team hosts can be found at github.com/opensuse-brasil/ and everything the team is aware of in south America is monitored on status.opensuse.net.br.

The openSUSE Project would like to thank all the companies and people who helped to improve the infrastructure in Brazil and South America.

Reach out to the team on the Brazilian openSUSE Telegram group.

Tue, Nov 1st, 2022

Balance of Power: A rematch served cold

There's an old video game the memory of which recently escalated itself to my attention: Chris Crawford's Balance of Power, a geopolitics simulator first released for the Macintosh in 1985. According to Wikipedia it sold about a quarter million units, which was a lot at the time, and I must've been somewhere in the impressionable age range of 10 to 12 years old when my father bought Incredible Technologies' port for the Commodore Amiga.

Go ahead and boop the nook

Its Workbench icon featured a mushroom cloud with a hand over it in the universal that's-not-what-I-ordered gesture (though possibly gently petting it — or simply shielding the observer's eyes?), but the game itself had a minimalist, academic look, and beyond a simple dissolve effect on the title screen it featured no explosions or indeed animations of any kind. This was unusual on the Amiga, a platform known for its ability to make the rubble bounce in Technicolor.

Crawford's maze

A strange game

Although I had an idea of what was going on in the world — I'd observed the cultural touchstones at friends' birthday parties, caught glimpses of something less watchable but much more memorable, and seen the inside of a bomb shelter — I didn't have the toolbox for nuclear brinkmanship, let alone internalizing what I now recognize to be a beautiful 87-page manual with a hardcover sleeve and an extensive bibliography. In the end, for all the sneaking into my dad's office to play this in the dead of night, I couldn't really figure it out.

So. Since Halloween seems like a good occasion to indulge in a little psychological horror (no other reason), I decided to do a rematch of sorts — this time with the help of fs-uae.

Crawford sez: RTFM

Crawford released an updated game in 1989 (simply called the 1990 edition), with the Amiga port credited to Elaine Ditton. It introduced the multipolar mode, which had been left out of the 1985 release:

Unfortunately, this multipolar view of the world is just too cerebral for most game players. It has something to do with our expectations of games; a mature, otherwise sophisticated adult will sit down with this game and ask, "How do I nuke the Commies?" Games, like stories, must have conflict, but people have been so inundated with the brutal, violent conflict standard in computer games that they are unable to grasp the subtle, indirect conflict arising from a multipolar world. This was a very painful discovery, and it forced a shift in the game from a multipolar view toward a more bipolar view. Minor countries had been able to pursue their own foreign policies; now they are passive pawns. Neutralist policies were entirely feasible; now minor countries choose up sides along left-wing/right-wing lines. The result is less realistic but more suited to the needs of the game-playing audience. Perhaps someday a more sophisticated game will be possible.

BOP manual, p. 74

Ok, so it's 2022 now, and we're all sophisticated down here. We want the multipolar. Furthermore, although the game didn't anticipate certain pivotal events of 1991, we'll play as the USA just to be on the safe side.

Here in the future, we also come armed with source code courtesy of the man himself: In this case, it's written in Pascal with a tiny morsel of assembler, of which the latter mostly exists to calculate square roots. BOP doesn't really have any spoilers apart from the obvious one, and a peek here and there should be interesting.

For the RAND analyst in you

Eh, close enough

The centerpiece of the game is, logically enough, the world map. It reflects some of the assumptions and technical limitations of the time: Many countries were removed because they'd make too small click targets or were thought to be strategically redundant. For instance, my own little corner of the world has been unceremoniously rolled into Sweden, which is fine (I, for one, welcome the Kalmar Union redux).

Next up, "Finlandization" is represented in the game, but Finland is not. This seems unfair to the Finnish. Of course, there's the unfairness of the entire, uh — (gesturing vaguely at the map) — to consider. It's very much not a game about curing the world's ills. But we'll live. Probably.

So neutral

Each country has a large number of variables attached. Some are directly manipulable, contingent on the limitations of physics and diplomacy. For instance, you could send military aid to the Swedish government but not the rebels, since there aren't any in Sweden to speak of. However, you could still intervene on behalf of these "rebels" and bootstrap an insurgency on some flimsy pretext. There are also subtle ways to change the existing government's mind and eventually sign a treaty that would let you station troops with them.

The important variables, such as government stability, security, affiliation and power, are only indirectly manipulable. Some of them are hidden, and most of them are obfuscated by natural language. There's no way you can break out your calculator to predict exactly what'll happen on the next turn, no big "Democracy" button to slam for a +2 bonus to semiconductors or whatever. You're forced to read reports and think in terms of… well, not exactly the real world, but at least a facet of it.

The game plays out over eight turns representing the passage of calendar years. On each turn, countries make their policy moves and optionally dispute each other's moves, and then the simulation ticks. The last part is where the magic happens. As an example, here's how country i's desire to Finlandize to superpower j is calculated:

FOR j:=1 TO 2 DO
    ProjPowr[j]:=(IntvConv(x)*ord4(MilPowr[j])) div MilMen[j];
    x:=(Should(x)*ord4(MilPowr[3-j])) div 128;
    SelfPowr[j]:=y+(x*ord4(Integrty[3-j])) div 128;
    IF SelfPowr[j]<1 THEN SelfPowr[j]:=1;
           div SelfPowr[j]);
    IF temp<0 THEN temp:=0; 
    IF temp>2048 THEN temp:=2048;
    FinlProb[j,i]:=temp div 8;

This is an interesting function with a couple of variables in play:

  • The government's military strength relative to insurgents' (MilPowr[i]-InsgPowr[i]).
  • The threatening superpower's military spending (MilPowr[j]/MilMen[j]) and ability to intervene in the area. InsgIMax(j,i) considers troops stationed in countries geographically adjacent to i.
  • The supporting superpower's military strength, treaty level and history of honoring its commitments (Integrty[3-j]).
  • The level of any diplomatic pressure campaign — harsh words, basically — aimed at the country (Pressure[j,i]). There's a small constant added to it, so the multiplier can never be zero; posting lots of soldiers next door can be quite menacing even if it's done quietly.
  • The adventurism factor (Adventur[j]), proportional to the demonstrated combativeness (Pugnacty[j]) of the threatening superpower relative to that of the other's plus the overall political tension in the world (Nastiness). This goes up if the situation seems dangerous and uncertain.
  • The diplomatic relationship between the threatening superpower and country i. This is a signed integer with 0 being neutral. Effectively, being on good terms neutralizes the threat posed by soldiers, but not that of general craziness.

Another delightful wrinkle is what happens if the superpowers put boots on the ground on opposing sides of a conflict, meaning the US and USSR are in a shooting war:

IF ((IntvGovt^^[1,i]>0) AND (IntvRebl^^[2,i]>0)) OR
   ((IntvGovt^^[2,i]>0) AND (IntvRebl^^[1,i]>0)) THEN
  BEGIN	{USA fights with USSR}

BOP treats this as an extremely serious situation and cranks up the Nastiness and Pugnacty factors, causing worldwide ripple effects (conflicts may erupt or worsen, weak governments may collapse, etc).

There's a lot more to it, but you get the idea: It's an interconnected world with gradual change, tipping points and cascading effects. I think few games pull this off — or dare attempt it — because it can leave a very narrow road between the extremes of boring (too stable) and incomprehensible (too chaotic). Throw in expectations of realism, and it's a tall order.

BOP manages fine, in part due to carefully chosen initial conditions and constraints on what it deems "minor" (non-superpower) countries. Here's Canada:


Defined as being contiguous with the USA (country #1), it adds Britain, France and West Germany to its sphere of influence, so when the AI hammers out its foreign policy, it will only consider these four counterparts. Britain for its part has 15, and France is up there with 12, but Sweden has only the one on its eastern border.

Frank exchange of opinions

{Returns a value of TRUE if the missiles fly}

Of course, countries don't get to undermine and invade each other willy-nilly. There are checks on this activity, such as the local neighborhood superpower getting on the phone and politely telling them to knock it off. When this happens to a minor country, it will pull back and just quietly stew for a bit, souring diplomatic relations, but with superpowers on both ends, things get exciting: It turns into a game of chicken. The superpowers take turns escalating, starting with a zero-stakes back-channel discussion, through diplomatic and military crises, until either one of them backs down or a nuclear war starts. The prestige penalty for backing down increases as the crisis escalates.

This can be frustrating, since it's easy to misjudge the computer's commitment (though it drops hints in its diplomatic missives, e.g. when it "categorically refuses" you may be about to have a bad day). The 1990 edition added advisors, in theory making it easier to get a read on the situation.

Mr. B has an idea

You can usually sort of interpolate their various opinions, but it's harder when they disagree wildly on an issue — like the above, where the Soviets just dispatched 20,000 soldiers to topple the government of Sudan. It sounds like a mean thing to do, and — more importantly — it would strengthen Soviet influence in the region and weaken ours. I don't think they're serious about this, so let's put our chips on advisor number four, the one with the mustache. I like his attitude.

No u

Mr. Gorbachev turns a deaf ear, so we go public with a diplomatic challenge. Still no. The world is watching now, and since there's an uncomfortable amount of prestige at risk, we press the issue and threaten a military response.


They escalate to DEFCON 4, we go to DEFCON 3, and they respond by escalating again. That's DEFCON 2, with bombers in the air and humanity collectively holding its breath. We're left with two choices: either let rip (and end the game) or back down and suffer crushing humiliation. This is bad. The prestige hit will affect our diplomatic relations, hamstringing us and effectively cutting our lead in half. Good thing we can absorb the loss without falling hopelessly behind. Otherwise, well…

Anyway. How could advisor #4 lead us astray? The answer lies in this excerpt from the GImpt() function:

x:=DipAff^^[i,Obj] div 4;
y:=(Should(Treaty[i,Obj]) div 4)+1;
z:=(ord4(DontMess[Obj])*1280) div SumDMess;
t:=Adventur[i] div 2;

  1: BEGIN x:=x*MySqrt(Abs(x)); y:=MySqrt(y); END;
  2: BEGIN y:=y*MySqrt(y); z:=MySqrt(z); END;
  3: BEGIN z:=z*MySqrt(z); t:=MySqrt(t); END;
  4: BEGIN t:=t*MySqrt(t);
       IF x>0 THEN x:=MySqrt(x) ELSE x:=-MySqrt(Abs(x));

The enum values 1-4 correspond to the different advisors. Looking at the fourth one, our guy is giving more consideration to Adventur[i] — the adventurism factor again, which frankly must've been pretty high at this point in the game — and less to our relations with Sudan. Our belligerence emboldened him, and we got some bad advice in return.

Again there's a lot more going on under the hood, and a lesson for budding diplomats:

This system produces some behaviors that may surprise you. For example, suppose that you as an American player gave economic aid to Nigeria. The Soviets take objection to this and start a crisis. You escalate, they escalate, and a nuclear war starts. The question on your lips is, why would those idiots annihilate the world over economic aid to Nigeria? The answer is, because you were willing to annihilate the world over Nigeria. Remember, it takes two to make a crisis. The computer figured that this just wasn't an important issue for you, and that, while trivial, it was still a more important issue for itself. It therefore stuck to its guns. […]

This raises a very important point about geopolitics. You could protest loudly, "But I do care about Nigeria! The computer can't assume what I'm really thinking!" You are absolutely right. Real-world diplomats don't know what's really going on in the minds of their interlocutors. They know perfectly well that today's words are only an expression of today's exigencies. The only thing they can rely on are the substantial events of the past. If you have built up a record of close relations with Nigeria, your behavior in a crisis will have to be taken seriously. If your record is of weak relations, then your behavior will not be taken seriously. The computer treats it that way. If you want to convince people that you're serious, you've got to lay the groundwork.

BOP manual, p. 77-78

Enough of that. Are ya winning, son?

Yeah, about that rematch. This isn't tic-tac-toe, so you can play it and win. Sort of.

Everyone gets a trophy

The main difficulty lies in us and humanity getting to this screen — although "kept the peace" tends to belie some dismal stuff unleashed along the way — after which we can relax and judge the result for ourselves.

As you can see, mistakes were made in 1995. Lest you judge me, the (now former) government of Mexico forced my hand! What followed made a lot of people unhappy, and then the French admin collapsed amidst the general chaos.

I did keep the green line up, though, so we'll call it the good ending. It took a few tries.

Unforeseen consequences

resource 'STR ' (705, purgeable) {
	"2* response* reply* answer* reaction*"

resource 'STR ' (706, purgeable) {
	"2* is coming* is being sent* is on its way* will arrive*"

resource 'STR ' (707, purgeable) {
	"2* via the North Pole.* over your northern border.* by ICBM.* by m"
	"issile courier.*"

It's not an easy game. You could know the rules like the back of your hand, and it still wouldn't eliminate the risks.

The crisis dialogue has one final surprise in store for us. As you click through the DEFCONs, there's a random factor that becomes increasingly relevant. It represents the likelihood of an oopsie:

CASE CrisisLevel OF
  2: x:=16;
  3: x:=8;
  4: x:=2;
IF DipAff^^[1,2]>0 THEN x:=0 ELSE x:=(x*(-DipAff^^[1,2])) div 64;
y:=Random div 128;
IF x>(Abs(y)) THEN BEGIN CrisisLevel:=1; ANWFlag:=TRUE; END;

Watch out for that ANWFlag! The risk is at its highest when going to DEFCON 2 with superpower relations bottomed out (as they'd be in a shooting war): (16 * 127 / 64) / 128 = 0.248, or roughly a 25% chance of unintended fireworks.

In most cases, the probability will be much lower. If your relations are merely kind of bad at -32, and you go to DEFCON 4, the risk is 1/128, or 0.8%. In the real world that's not so low, but for the purposes of BOP it's a low probability/high impact risk you'll be taking again and again.

Good thing, then, that we only have to make it through eight years. The risks add up over time, and even if you play quite carefully, you will come to fear a certain arresting memo:

Thanks, I'm good

The "END" button drops you back to the desktop. In order to succeed at this game you need patience, a cool head and plenty of luck.

Learnings from Building an AppImage

For some time I am offering an AppImage of Kraft to make installations for users as easy as possible. Unfortunately real linux packages are big effort for the variety of distributions, and having one way to rule them all seems very appealing.

My first AppImage versions were pretty faulty when looking into details. So I spent some time to improve it recently, with the great help of the friendly people from AppImage community.

Here is my little report about what I have learned. If there is something I can do better, please let me know (unless it is use $OTHERTOOL).

How to build an AppImage?

At first, it makes sense to build the AppImage automatically via Github Actions. GH Actions are powerful, and well integrated. I also looked into using the openSUSE Buildserver for that, which works, but Github Actions seemed easier.

I got convinced by @TheAssasin to use AppImageCraft to build the image. That simplifies the process significantly by hiding a lot of auto generating things under the hood. While that leads to very clean and short config files for the AppImage build, it is harder to deal with issues that might come up because things are covered.

If I would not have had help from the dev that I know personally, I probably would not have survived the process. Yet, AppImageCraft is an awesome utility, yet a bit better documentation would help a lot.

Python Components

Kraft has a few Python components that are called from Kraft to do specialized tasks that I did not want to reimplement in C++. For example, it uses the awesome tool weasyprint to generate PDF from html.

While the AppImage can call a weasyprint installation that is installed on the host system that is not a good solution as there is no way to control if the required tool is really installed. So bundled Python is needed with all the dependencies for the external deps.

To achieve that, there is a very useful linuxdeploy-plugin called conda that uses conda to install Python. It installs the required python libs via pip and make them available in the bundle. Very convenient.


To be a good citizen in the AppImage world, the app needs to be careful with pathes. When running in the AppImage, it is advisable to not use for example classes like QStandardPath directly or even worse hardcode paths that do any loading of files the app needs. Since the file tree of the AppImage is just mounted somewhere in the host system, the app needs to consider that it is not installed in standard locations.

A good rule of thumb when locating a file to load is to always check relative to the binary path first (ie. ../share/kraft/data/), and if that does not exist, continue to check the standard paths of the host system.

In Kraft there were already utility methods to adjust paths which I could simply extend to work fine in the AppImage. Still, that is kind of fiddly as there are more places to consider than one expects.

Locate translation files

Also a result of the challenge described before is that the app did not find the translation files to load in the filesystem of the AppImage. The translation system (KLocalizedString in Kraft) does obviously not check the correct path inside the AppImage mount.

Setting an additional relative path to look up translations at runtime fixes that problem.


Another issue that required quite some work were icons. Kraft used icons from the system theme quite a lot. As long these are installed, because the user has the same fitting desktop environment, that is not an issue, and icons are found.

However, if the icon theme is not installed, the app just lacks icons which make it bad looking or even hard to use.

That can be solved by using own icons as fallback in the app. For simplicity and consistency I switched to a complete set of own icons that are now coming with Kraft. They are bundled to the app with the Qt resource system now.

Dependencies to the Outside

Last but not least: When preparing an app for AppImage it needs to be checked if the app has binary dependencies that can (or should) not be packaged into the AppImage for efficiency reasons. Kraft for example uses Akonadi for contacts. With that users can use KAddressbook to manage addresses and Kraft uses the address lists via Akonadi. Life is too short for reinvention of an Addressbook.

Of course one could think of bundling the entire Akonadi and KAddressbook into the AppImage of Kraft. But that seems overkill, as that would mean bundling a lot of stuff, and would bring KDE users two instances of KAddressbook (the one from their desktop installation and the one from the AppImage). Seems not a good idea.

So this seems to be the only downside of the new Kraft AppImage now: It can not use the Akonadi based address management. To fix that, there needs to be a non binary dependant way. There could for example be a way to sync contacts to a local file system and let Kraft pick them up from there. That way, users could use the address management they want (also for example google) and Kraft could still pick addresses from there. That needs more thoughts.

The good news on this that Kraft is still fully functional as the Akonadi integration is great, but optional.


An AppImage seems to be a great way of distributing desktop applications, because there is only one build to run on all distributions. Well, fingers crossed…

However, building an AppImage that really works flawlessly is not a simple task, as this blog hopefully illustrates a bit.

One thing would have helped me: A simple option to understand when the app loads things from the host system, rather than from within the AppImage, for example as commnd line switch when running the AppImage. That would have eased the path adjustment development described above.

What is next in that area: User friendly updating of the AppImage and a solution to the address management problem.

All changes were merged in Kraft master today, the resulting AppImages can be found here.

Sun, Oct 30th, 2022

Pixel Inktober

Just like last year, October was filled with quick pixel dailies. I decided to only post on mastodon, but due to the twitter exodus couldn’t quite post the 30kB images for the two remaining days. Good old blog post it is!

x 1. Gargoyle 2. Scurry 3. Bat 4. Scallop 5. Flame 6. Bouquet 7. Trip 8. Match 9. Nest 10. Crabby 11. Eagle 12. Forget 13. Kind 14. Empty 15. Armadillo 16. Fowl 17. Salty 18. Scrape 19. Ponytail 20. Bluff 21. Bad Dog 22. Heist 23. Booger 24. Fairy 25. Tempting 26. Ego 27. Snack 28. Camping 29. Uh-oh 30. Gear 31. Farm

Previously, Previously, Previously.