bcal: a REPL calculator for byte expressions, LBA/CHS and base conversion
:1234: Bits, bytes and general-purpose calculator
At a glance
- What is it?
- bcal is a GPL-3.0 C utility that evaluates arithmetic on storage units, converts between SI and IEC prefixes, and translates disk addresses. It is aimed at people who type byte counts all day and want one binary instead of a browser tab.
- Who is it for?
- Adopt bcal if you routinely compute byte offsets, convert between kB and KiB, or translate LBA and CHS by hand, and you want a single small C binary that also handles general arithmetic. Skip it if you need arbitrary-precision maths, floating point formatting control, or a library to embed; the README describes 64-bit operating systems only, and the expression grammar is the five storage operators plus a fixed function list.
- Can I use it commercially?
- Yes, with conditions. GPL-3.0 is a copyleft licence: if you distribute software that includes it, you must release that software's source code under the same licence. Running it internally without distributing it does not trigger that obligation.
- Is it still maintained?
- Yes. The repository last received commits 11 days ago.
- What is it written in?
- Mainly C, according to GitHub's language statistics.
Answers come from the project's GitHub data, last synced on September 15, 2026, and from our analysis. They are not legal advice.
DEEP OPEN-SOURCE ANALYSIS
The gap bcal fills: arithmetic where the unit is part of the number
Most calculators treat a number as a number. If you want to know how many 4 KiB pages fit in 3 GiB, you either convert both to bytes by hand or you look up the multiplier. bcal takes the unit as part of the operand. The README's own example is "(2GiB * 2) / (2KiB >> 2)", which mixes multiplication, division and a right shift inside one expression, with the shift applied to a unit-bearing value. The target user is someone who reads disk layouts, partition tables, firmware images or memory maps, and who already knows that KiB and kB are different things. The project describes itself as useful for those who deal with bits, bytes, addresses and binary prefixes frequently. It is not a spreadsheet replacement and it is not a symbolic maths package. It is a terminal tool for a specific class of question: how big is this, and where does it land on the disk.
Two modes, one binary: storage expressions and a general maths REPL
bcal runs either as a REPL or as a single-shot command. With no arguments it enters the REPL, and the prompt tells you which mode you are in: bytes> for storage mode, maths> for general-purpose mode. The prompt key b toggles between them, so general-purpose work is reachable without restarting. The last valid result is kept in a variable named r, and the r key at the prompt prints it. That result reuse is the main reason to stay in the REPL rather than shelling out repeatedly: you can compute a size, then feed it into a conversion without retyping digits. In single execution mode the expression must be quoted, and inner spaces are ignored. Storage expressions accept +, -, *, / and %. General-purpose mode widens this to bitwise operators AND (&), OR (|), XOR (^), complement (~), lshift (<<) and rshift (>>), plus functions exp(n), log(base, n), ln(n), pow(n, exponent), root(radical, n) and sum(n1 n2 ...). The split is deliberate: the storage grammar stays small and predictable, and the bitwise and function surface lives behind -b or the b prompt key.
Conversions that are not arithmetic: base, bit position, address and CHS
Three of bcal's options are lookups rather than evaluations. The -c N flag shows a positive integer N in binary, decimal and hex, and the same operation is available at the prompt as c N. The -p N flag shows bit positions with the bit value for N, again mirrored as p N at the prompt. The -f loc flag converts CHS to LBA or LBA to CHS, and the README points at the operational notes in the man page for the expected input format, which is a signal that the syntax is not guessable from the flag name alone. Address output has two forms: show the address in bytes, and show the address as LBA:OFFSET. Sector geometry is configurable through -s bytes for sector size (default 512), and the feature list mentions custom sector size, max heads per cylinder and max sectors per track. Those geometry knobs matter because CHS translation is only meaningful relative to a specific drive layout. The -m flag switches to minimal output such as decimal bytes, which is the form you want when piping into another command, and -H prints integral maths results in hex.
Getting it installed: make targets and the readline decision
The dependency list is short: standard libc plus GNU Readline, or BSD Editline as an alternative. Readline can be removed entirely. Building with O_NORL=1 uses a native input prompt with history file support instead. The default install path is /usr/local, so the basic build is sudo make strip install. To link against libedit, use sudo make O_EL=1 strip install. To drop the readline dependency, use sudo make O_NORL=1 strip install. For a static binary there is O_STATIC=1, which the README notes forces O_NORL=1, and there is a static target that does the same thing. PREFIX is supported if you want a different install location, and uninstall is sudo make uninstall. Musl builds are documented through the compiler variable: CC=musl-gcc make, or CC=musl-gcc make O_STATIC=1. On Termux for aarch64 Android the README gives a full sequence: download the master zip, unzip, cd into bcal-master, pkg install make clang readline-dev, then make strip install. The O_NORL path is the interesting one for anyone building containers or minimal images, because it removes the only non-libc dependency.
Input handling: piped data, file redirection and where the REPL assumption breaks
The feature list states that bcal works with piped input or file redirection. That is what makes it usable inside scripts and one-liners, and it is the mode where the -m minimal output flag earns its place, since you want a bare decimal byte count rather than a formatted conversion table. The limitation follows from the same design. The REPL holds state in r, and state does not survive a pipe. If your workflow depends on carrying a result from one expression into the next, you are either staying interactive or you are chaining separate invocations and re-supplying values. There is a second boundary in the README itself: bcal supports 64-bit operating systems only. That is stated without qualification, so on a 32-bit target the project is not a candidate at all. The arithmetic surface also has a ceiling. The function list is fixed at exp, log, ln, pow, root and sum, and the README does not describe arbitrary-precision or big-integer behaviour, so expressions that need more than native word width are outside what the documentation claims. The -c and -p flags both specify a positive integer N, which means negative operands are not part of those two operations as documented.
Where bcal sits next to a general maths REPL like bc
The obvious alternative for terminal arithmetic is bc, which ships with most Unix-like systems and is a general arbitrary-precision calculator language. The approaches differ in what the tool knows about. bc knows numbers and a small programming language; it has no concept of KiB, no LBA, no CHS, no bit-position display, and no storage-unit output formatting. You can compute 2*1024*1024*1024 in bc, but the 1024 is your job to remember and the result is a bare integer. bcal inverts that: the unit is syntax, and the conversions that follow from byte counts (SI versus IEC, base, bit position, disk address) are built in. The cost of that specialisation is reach. bc handles arbitrary precision and scripting constructs that bcal's documented grammar does not mention. So the choice is not about which is better. If your problem is a byte count, a disk address or a prefix conversion, bcal carries the domain knowledge. If your problem is a long numeric computation or a loop over values, bc is the tool that was built for it, and bcal will not substitute.
Release cadence, licence and what to check before you depend on it
The release history in the supplied material shows v2.4 in January 2022, v2.5 in February 2026, and v2.6 in September 2026. That is a long quiet stretch followed by two releases in the same year, which is worth knowing if you are pinning a version: check which release your package manager actually carries, because the README itself advises trying an alternative installation method if the packaged version is dated. Building from source is the fallback, and the make options above are the ones you would use. The licence is GPL-3.0. That matters for how you can redistribute bcal or a modified version of it, and it is not a licence you can relicense into a permissive project. If you are considering shipping bcal inside a product rather than installing it on a workstation, the GPL-3.0 terms are the first thing to read, and this article is not legal advice. On maintenance cost, the dependency surface is small enough that the main ongoing question is which build flavour you standardise on: readline, editline, or the O_NORL native prompt. Pick one and record it, because the three produce different interactive behaviour and only the O_NORL one removes the external library requirement.
Editorial conclusion
Adopt bcal if you routinely compute byte offsets, convert between kB and KiB, or translate LBA and CHS by hand, and you want a single small C binary that also handles general arithmetic. Skip it if you need arbitrary-precision maths, floating point formatting control, or a library to embed; the README describes 64-bit operating systems only, and the expression grammar is the five storage operators plus a fixed function list. Before relying on it, verify three things on your own machine: that your package manager ships v2.6 or that you can run make strip install, that your sector size assumption matches the default of 512 bytes unless you pass -s, and that the CHS geometry you feed to -f matches the drive you are describing.
Community notes