BusyBox ash vs GNU Bash
When we released Sailfish OS 4.0.1 in early 2021, the default shell was changed from GNU Bash to BusyBox ash. GNU Bash is still available in the repositories, but it’s not installed by default. In today’s article, we will have a look at the differences between the two shells.
Short history of shells.
BusyBox ash is one of the shells included in BusyBox, the other one being hush. BusyBox ash is a derivative of the Debian Almquist Shell ‘dash’, which in turn is a derivative of the Almquist shell. The Almquist shell is a lightweight Unix shell from the 80s, originally a clone of Bourne shell.
GNU Bash is a shell included in the GNU project. It was originally written to be a compatible replacement for the Bourne shell. So it can be seen as a great uncle/aunt of busybox ash.
Same but different
GNU Bash has added several features on top of the POSIX shell standard. While we have built BusyBox ash with the bash compatibility options, there are differences. In practice this means that quite often shell scripts targeting GNU Bash need changes before they work on BusyBox ash. On the other hand, both shells are POSIX compliant, so shell scripts targeting POSIX shell should work on both without changes.
Below I will go through some differences that we have found while adapting our scripts to BusyBox ash. Please note that this is definitely not a complete list of the differences between the shell, but just some things that we have faced during the transition. Neither is this a complete list of changes made to the scripts in the process, as in many cases we have targeted POSIX compatibility, even if it’s not a strict requirement in order to work with BusyBox ash.
Here document delimiters
Let’s say you have the end delimiter of your here document on the same line as the ending parenthesis of your assignment, like this:
FOOBAR=$(cat - <<-EOF
FOO
BAR
EOF)
That is an error - “EOF” should be on a line by itself. But bash forgives this kind of errors, it just prints a warning. Busybox is not as forgiving and it will just fail.
Here strings
While BusyBox ash understands here-documents, it does not understand here strings.
In most cases it’s easy to pipe the output of echo
instead of using a here string. For example, echo "${VAR}" | grep --quiet searchstring
instead of grep --quiet searchstring <<< "${VAR}"
.
shopt
Bash includes shopt builtin for controlling and querying optional shell behaviour. BusyBox does not have such a thing, so we have to use other means.
One such use case is checking whether a script is executed on a login shell with shopt -q login_shell
. One way of performing similar check is to look at the first character of arg0 - On login shells it starts with a hyphen. So, [ "$0" != "${0#-}" ]
returns true on a login shell.
Brace expansion
Bash can generate arbitrary strings using brace expansion. As BusyBox does not support this, we have to write each string separately: foo{bar,baz}
needs to be written as foobar foobaz
.
Wildcards in string comparison
Bash allows using wildcards in string comparison. Say, you want to check if string starts with “foo”. You could simply write: if [[ "$mystring" == foo* ]]; then ...
. Or, if you want to check if the string has “foo” anywhere in it, you would write: if [[ "$mystring" == *foo* ]]; then ...
With BusyBox this kind of construct is not available, so we have to use some other way of checking. There are several ways of doing this, for example using grep: if echo "$mystring" | grep -qE "^foo"; then ...
Another possibility is using substring parameter expansion, which is a POSIX feature: if [ "$MYSTRING" != "${MYSTRING#*foo}" ]; then ...
Arithmetic evaluation in conditionals
Bash allows (( ))
arithmetic evaluation with conditionals, e,g if (( myvalue == 1 )); then
Again, this can be implemented in multiple BusyBox compliant ways. A simple “equals” check can use -e comparison: if [ myvalue -e 1 ]; then
. If you have a more complex expression, you can first evaluate it with the let
builtin and then compare the results.
Environment variables
On startup, bash sets environment variables UID
and EUID
to match the current user ID. Busybox does not do this. This is easy to remedy by using id -u -r
and id -u
commands.
Startup scripts
There are also some differences related to the scripts which the shell reads on startup. Bash tries to determine if it’s being run over a network connection - like ssh, and in such cases it reads the usual startup scripts. Busybox by default does not do this, so you might get surprising results when you execute commands over ssh. We have patched our version of busybox ash so that it mimics bash behaviour more closely, but I figured I should mention it anyway.
App roundup
It feels like we have all of life reflected in our app selection for this newsletter. Either that’s a testament to the ingenuity of Sailfish OS app developers, or an indication that my life experiences aren’t as multifaceted as I like to think. I maintain the former of course, and there’s no denying the variety on offer here, spanning a spectrum that includes maths, conversation, work and play. We hope you find something here to enjoy, and with at least one totally new app on offer here, maybe even something you’ve not tried before.
Fibonacci
Fibonacci is a new app from prolific app developer and maintainer Mark Washeim (poetaster). It’s an impressive piece of work, combining multiple elements in a dizzying array of capabilities. In many senses this is two entirely different apps: first a Reverse Polish Notation calculator, and second a programmable calculator using a C++-like language.
Let’s start with the first. Most normal calculators expect you to input expressions from left-to-right as you would on a page. But RPN is different: you enter the variables up-front, followed by the operator. This approach can take a while to get used to, but once mastered makes entering expressions fast and easy. You no longer have to worry about precedence, or operators that take more than two variables. Things just fall into place.
But this is more than just an RPN calculator. Under the hood the app is built on SymPy, a symbolic maths library that deals with algebra rather than numbers. In practice, that means you can enter mathematical expressions, simplify them, and not lose any precision until you want to boil your calculation down to a number at the end. It will also comfortably handle complex numbers too.
The second is a programmable calculator that uses the exprtk library to efficiently run simple programs using a C++ style of notation. It’s not exactly C++ and it took me a little while to get the hang of the syntax. The error messages aren’t always the most helpful. But it ultimately lets you define and execute — theoretically at least — any computable function.
Mark is very clear that this is still a work in progress. “It may eat your machine” he explains in the description “But I like it”. And so do we. At version 0.9,1 it’s already a very capable tool. Mark also has big plans for it, using the SymPy engine to perform calculus, amongst other things. This is all very promising, and makes Fibonacci one to watch.
Fibonacci is available from the Jolla Store, OpenRepos and Chum.
ChatGPT
Although we looked at the ChatGPT app from Dominik Chrástecký (Rikudou_Sennin) only a month ago, Dominik has been developing it rapidly, so we thought it would be worth heading back to take another look. When we last looked at it, it was on version number 0.9.6. It’s now on 0.9.10 having enjoyed three other releases in between.
In case you’ve not heard the news, ChatGPT is the impressively competent chat bot from OpenAI that uses a large language model to generate textual answers to any question you want to throw in its direction. It will find information for you, summarise text, answer programming problems. If you’re feeling brave it will even try to do maths, although not always with the most successful outcomes.
In general, it’s good to have some healthy scepticism about any of the answers it provides, but it’s also a multifaceted tool with potentially far-reaching utility.
The app allows you to indulge in conversations with the ChatGPT chat bot. You’ll need an OpenAI API key to do this, but the description explains how you can do this (getting one is “free as in beer”, as long as you’re not too concerned about the privacy consequences). The latest updates add the ability to use GPT-4, the latest and greatest backend, as long as your API key supports it. Perhaps more relevant for many users is the ability to switch between languages (currently English, Czech, Swedish and Polish). It’s nice to see Dominik continue to improve the app and keep Sailfish OS on the cutting edge.
ChatGPT is available from the Jolla Store, and OpenRepos.
Patience Deck
Regular readers of the newsletter will be familiar with Patience Deck from Tomi Leppänen (tomin). It provides not just a deck of virtual cards, but what you might call a deck of decks of virtual cards. By which I mean it incorporates any astonishing ninety different card games, complete with rules and explanations, all in the one diminutive app.
Back in November of last year Tomi announced a call for feedback, asking users for input to add to the app’s issue tracker. Since then he’s been working through the suggestions and gradually improving the app based on them.
This process has borne some very ripe and delicious fruit. My particular favourite is the animated celebration of exploding cards that you’re treated to if you win a game, à la Windows 95! But that’s not all. Since we last looked at the app it’s gained an improved button bar with the option to start new games as well as repeating the existing game, with new graphics and an undo option that straddles restarts.
It’s impressive stuff, and well worth the upgrade. This has to be the best card game app for Sailfish OS, and you’d be hard pressed to find something better on any platform.
Patience Deck 1.0.1 is available from the Jolla Store and OpenRepos.
Hafenschau
Samuel Kron (black-sheep-dev) bills his Hafenschau app as “an unofficial content viewer for German News Portal tagesschau”. It provides a slick QML-based interface to the news site, making it easy to pick out and read news stories — images and all — without having to resort to accessing the site through the browser.
The app provides categorised channels: domestic, foreign, economic, investigative news, and so on. You can also choose regional news stories based on a regional setting you specify directly within the app. It also has a handy search facility in case you’re looking for something specific or historical.
It’s a German news site, and so unsurprisingly the articles are in German. But as long as this isn’t a blocker for you being able to read the news stories, you’ll find the app a very worthwhile addition to your phone.
The latest updates seem to have been precipitated by service-side API changes that affected media and images, as well as updates to fix the packaging.
Hafenschau is available from the Jolla Store, OpenRepos and Chum.
Repository roundup
The network stack
-
connectionagent
, a daemon and QML bindings to connect to ConnMan, abranson modified the DBus interface so Wifi tethering and Bluetooth tethering can be manipulated separately. Previous, the tethering API was implicitely dealing with Wifi thethering only. The pull request has not been accepted yet. -
ssu-sysinfo
, tools and libraries for getting ssu information, abranson proposed a patch exposing Bluetooth thethering hardware feature. -
nemo-qml-plugin-systemsettings
, a QML component used by the Settings app, abranson proposed a patch to expose Bluetooth thethering hardware feature. -
connman
, the connection manager, LaakkonenJussi reversed the commit adding longer timeout to establish connection. It seems that it’s not solving the problem.
The telephony stack
-
voicecall
, the open source part of the calling application, Michal-Szczepaniak proposed to package again the header files, so plugins can be compiled againstvoicecall
.
Calendar stack
-
mkcal
, storage backend using SQLite for calendar entries, dcaliste cleaned internal class not to useQSharedPointer
when not necessary. dcaliste also modified the API of the purge function to restrict it to a given notebook. He is working on the deprecation of notebook support fromKCalendarCore::Calendar
in KDE, with two pull requests, one separating the SQLite operation from the memory operations and another one implementating new storage classes. -
nemo-qml-plugin-calendar
, the QML bindings for calendar events, dcaliste restricted the event purging from database to the correct notebook. This is a required step to support incidences with the same UID in different notebooks, allowing then to be able to move events between notebooks. -
buteo-sync-plugins-social
, several sync plugins for Google, Facebook and other proprietary protocols, dcaliste restricted here also the event purging. -
buteo-sync-plugin-caldav
, the synchronisation framework plugin for CalDAV content, dcaliste restricted here also the event purging. dcaliste also opened a pull-request demonstrating the use of a single notebook storage, as newly introduced in mKCal.
Low level libraries
-
sensorfw
, sensor framework, lgtrombetta proposed to fix calibration issues of the magnetometer. The patch has been tested on the PinePhone and is proposed by the Ubuntu touch community. -
libxml2
, an XML parsing library, mal updated it to 2.10.4 fixing two CVEs. -
droidmedia
, Android media wrapper library, mal has started working on porting to Android 13. -
libngf-qt
, Qt-based client library for Non-Graphic Feedback daemon, pvuorela set up a different feedback for non-touch haptics (to dissociate them from display ouch events). He also silenced play failed signals, since they can come from just the haptic feedback being turned off. -
libmce-glib
, Glib client for mce, spiiroin added support forMceInactivity
which expose device inactivity. The pull request also contains a commit adding a example program on how to use the Glib bindings to Mce. -
sailjail
, a wrapper around firejail, vigejolla added a missing build dependency.
SDK and developer tools
-
amber-web-authorization
, a QML module allowing applications to perform OAuth1 and OAuth2 requests, vigejolla migrated its documentation to use Sailfish template instead of Mer one. -
sdk-user-manual
, examples and documentation for the SDK, vigejolla also migrated the documentation of this package. -
sdk-harbour-rpmvalidator
, the harbour validation scripts, vigejolla made the validation fails when there are triggers in the generated RPM. He also strictened the dependencies between packages, banningConflicts
,Recommends
,Suggests
,Supplements
andEnhances
in addition to already forbidden usage ofObsoletes
. -
sailjail-permissions
, the configuration files for system-wide sandbox permissions, vigejolla added a sentence explaining thePrivileged
permission and restricted it for internal purposes only. -
nemo-qml-plugin-notifications
, QML bindings to the Freedesktop notification system, vigejolla fixed the links to the specification in the documentation.
Sailfish OS website
-
nephros mentioned that while WEP encryption is still proposed, it has been actually deprecated and already removed internally, see WLAN Troubleshooting | Sailfish OS Documentation
-
karry clarified the article on native map applications, see Maps and Location service | Sailfish OS Documentation
-
jovirkku added a page explaining how to export calendar data, see Calendar Exporting Data | Sailfish OS Documentation . He also complemented the People application page explaining how to export the contact database to a file in VCF format, see People App and Contacts | Sailfish OS Documentation and later on added a description on how to import contacts from a VCF file, see Importing Contacts | Sailfish OS Documentation
-
jpwalden added a tips on how to remove stuck notifications using the command line, see Tips and Tricks | Sailfish OS Documentation
-
jovirkku added a checklist to help people struggling with the various steps to flash a device, see Checklist for Sailfish OS | Sailfish OS Documentation . He later amended it with details on how to enter fastboot mode.
-
jpwalden complemented the Calendar application article mentioning how to remove the calendar database, see Calendar | Sailfish OS Documentation
-
The reference page table of content is now automatically generated with vigejolla’s patch, see Reference | Sailfish OS Documentation
-
jpwalden created a page describing how to collect logs from the Camera application, see Collect Camera Logs | Sailfish OS Documentation and another one for the location services, see Collect Location Services Logs | Sailfish OS Documentation
-
MPolleke gathered the information about the Ambience system and created an article for developpers, see Ambience | Sailfish OS Documentation
Please feed us your news
Thanks for reading! Please keep sending us the suggestions for future topics.