10. NEWS
10.1. bitmath-2.1.0
Released: May 24, 2026
bitmath 2.1.0 is a focused follow-up to the 2.0.0 modernization. It finishes the last of the Python 2 cleanup, tightens the project’s quality tooling, retires one piece of legacy API surface, and works through OpenSSF’s full menu of supply-chain checks (Scorecard, Best Practices, and the OSPS Baseline) to put a credible security posture on the record. The public API is essentially unchanged from 2.0; the two breaking changes below are narrow ones that affect internal-type inspection and one deprecated helper.
10.1.1. Breaking Changes
- Internal representation is uniformly floating-point
Every bitmath instance now stores its size as a 64-bit float, no matter which constructor created it. Previously the
bytes=andbits=keyword constructors, along with the bit-family value constructors such asKib(N), leaked Pythonintvalues through the.bytesand.bitsproperties. Those properties now always returnfloat, matching the long-documented floating-point measurement design described in the Rules for Math appendix. Equality, ordering,repr(), and arithmetic results are unchanged; only code that inspectedtype(instance.bytes)ortype(instance.bits)directly will observe the difference.- listdir() is deprecated
bitmath.listdir()now emits aDeprecationWarningon every call and will be removed in a future release. Iterate withos.walk()and callbitmath.getsize()directly instead. Closes issue #27.
10.1.2. Library Improvements
- pathlib support
bitmath.getsize()now acceptspathlib.Pathobjects, not just strings, for itspathargument.
10.1.3. Project Infrastructure
- Linting moved to pylint
pylint replaces flake8/pyflakes across the CI workflow and the local toolchain, and the library is held at a 10.00/10 score. pycodestyle is retained for the PEP 8 whitespace checks pylint does not cover.
- Security scanning with bandit
Bandit is a static analyzer from PyCQA that scans Python source for common security smells (hardcoded secrets,
eval,subprocesscalls withshell=True, insecureyamlandpickledeserialization, weak crypto primitives). It runs as part ofmake ciand as a dedicated GitHub Actions workflow that fires on every push, every pull request, and on a weekly schedule, scanning bothbitmath/andtests/.- 100% test coverage
The remaining coverage gaps were closed, including the platform-specific
bitmath.query_device_capacity()branches, bringing the suite to 100% measured coverage on every supported platform.- Property-based testing with Hypothesis
Four
@givenproperties coverbitmath.parse_string()roundtrips, lossless unit conversion across every(src, dst)pair inbitmath.ALL_UNIT_TYPES, and the contract thatbitmath.parse_string()raises onlyValueErroron bad input. The roundtrip property already turned up a real parser bug around scientific-notation float formatting, which is filed as a follow-up. See PR #144.- SPDX license headers
Every source and test file now carries
SPDX-License-IdentifierandSPDX-FileCopyrightTextheaders.- Single-sourced version
The package version is read dynamically from the
VERSIONfile by hatchling, so bumping that one file propagates everywhere.- Signed releases (landing with 2.1.0)
The 2.1.0 release closes out the open OSSF Scorecard Signed-Releases finding (“Determines if the project cryptographically signs release artifacts,” currently flagged at high severity). Scorecard should reflect the improvement on its next weekly run after the release lands.
10.1.4. Security and Supply Chain
Most of the work in this release happened here. OpenSSF’s supply-chain story has matured enough to be worth pursuing in earnest even on a small library like bitmath, and the project now carries the badges and the automation to back them up.
- OpenSSF Best Practices passing badge
bitmath earned the OpenSSF Best Practices passing badge. The full self-assessment is on the linked profile; the badge appears on the README and the docsite landing page alongside the OSSF Scorecard and OSPS Baseline badges.
- OSPS Baseline Levels 1 and 2 (Level 3 mostly)
OSPS Baseline Level 1: 23 Met, 2 Not Applicable, 0 Unmet. Level 2: 19 Met, 0 Unmet. Level 3: 18 Met, 2 Not Applicable, 1 Unmet. The single Unmet at Level 3 is OSPS-QA-07.01 (non-author code review), which is structurally blocked by this being a single-maintainer project. Closing it would require either onboarding a second maintainer or changing the project governance model, neither of which is happening in 2.1.0. The control responses backing each Met assessment live in the docsite under Project Architecture and the policy documents listed below.
- OSSF Scorecard
.github/workflows/scorecard.ymlruns on every push tomaster, on branch-protection-rule changes, and on a weekly cron. Current score and history are published at https://securityscorecards.dev/viewer/?uri=github.com/timlnx/bitmath.- GitHub Actions pinned to commit SHAs
Every GitHub Actions reference in
.github/workflows/is now pinned to a full-length commit SHA with the version as a trailing# vX.Y.Zcomment. Floating tags (the old@v4) and floating branch refs (the now-removedMishaKav/pytest-coverage-comment@mainthird-party step) are gone. Dependabot keeps the SHAs fresh.- Dependabot
.github/dependabot.ymlwatches thegithub-actionsandpipecosystems on a weekly cadence. Minor and patch bumps are grouped per ecosystem to keep PR noise bounded; major bumps land as standalone PRs so breaking-change review stays honest.- Hardened workflow token permissions
Every workflow declares an explicit
permissions: read-allat the top level, withwritescopes applied only to the jobs that need them (security-events: writefor SARIF upload,id-token: writefor PyPI OIDC Trusted Publishing, and so on). The default-writeGITHUB_TOKENposture is no longer inherited anywhere.- SCA via pip-audit
.github/workflows/sca.ymlruns pip-audit on every push, every pull request, and on a weekly cron. bitmath has no runtime dependencies, so this scans the test-only deps inrequirements.txt. Findings are resolved on the release-blocking timetable specified inSECURITY_POLICIES.md.- CycloneDX SBOM attached to every release
The publish workflow now installs the built wheel into an isolated venv, snapshots it with cyclonedx-py, and attaches the resulting
bitmath-<version>.cdx.jsonto the GitHub release alongside the wheel and sdist. Downstream consumers who SBOM-scan everything they ingest can now pull bitmath’s SBOM from the release page directly instead of generating their own.
10.1.5. Project Documentation and Governance
The documentation set picked up five new top-level files this release. These exist to answer standing security, governance, and verification questions for downstream consumers without requiring a real-time email exchange, and several of them are direct deliverables for OSPS Baseline controls.
- MAINTAINERS.md
New top-level file naming the sole current maintainer, the sensitive-resource access that comes with the role (PyPI account, GitHub admin, GPG key, ReadTheDocs admin), maintainer responsibilities, and a standing open call for a Debian/Ubuntu co-maintainer (see issue #117 if you’re interested).
- ARCHITECTURE.md
New top-level design document covering runtime architecture, the build and release pipeline (including the Packit downstream RPM flow into Fedora and EPEL), CI gates, trust boundaries, and the documentation pipeline. Lives at the repo root so the OpenSSF scanner finds it by filename, and so anyone exploring the repo for the first time can get the design picture before reading code.
- SECURITY_ASSESSMENT.md
Standing threat model describing the attack surfaces (supply chain, PyPI account, source repository, build chain, distribution chain), the mitigations in place for each, and the automated security tooling stack with what each tool catches.
- SECURITY_POLICIES.md
The SAST and SCA remediation thresholds and release-blocking criteria in one place. Bandit and pip-audit findings, severity ladder, the rule for what blocks a release versus what gets a follow-up, and the timetable for acting on each.
- VERIFICATION.md
Downstream-consumer guide for verifying a bitmath release end to end: integrity via the SHA-256 sums published alongside the GitHub release, authenticity via PEP 740 attestations and pypi-attestations, and provenance via the CycloneDX SBOM. If your organization’s policy requires verifying every dependency before installation, this is the playbook.
- SECURITY.md tightened up
Coordinated Vulnerability Disclosure now states explicit response timeframes (72 hours to acknowledge a report, 7 days to triage), and the document picked up new Scope of Support, Duration of Support, and Secrets and Credentials Policy sections.
- HTTPS for all project doc URLs
Every
http://reference to project-owned documentation (bitmath.readthedocs.io, the docsite, README badge targets, NEWS historical links, CONTRIBUTING) has been switched tohttps://to clear the bestpractices.devsites_httpscheck. ReadTheDocs was already serving TLS; only the scheme needed flipping. See PR #146.
10.2. bitmath-2.0.0
Released: April 25, 2026
Nearly eight years after 1.3.3 shipped in 2018, bitmath is back with a major release. Version 2.0.0 is a thorough modernization: the Python 2 era is officially over, the library picks up several long-requested features, and the entire project infrastructure has been rebuilt from scratch. If you’ve been running bitmath on Python 3.9 or later and quietly wishing it felt more modern — this release is for you.
Check over on my blog for a personal recap of this release, how much it means to me, and what it took to get here.
10.2.1. Breaking Changes
- Python support
Python 3.9+ only. Python 2 and Python < 3.9 are no longer supported or tested.
- parse_string() default system
The default unit system when
strict=Falseis now NIST (base-2). Previously it defaulted to SI (base-10). Code that relied on the old default for ambiguous strings such as"1g"could get a different result. See parse_string with strict=False for full details. All bitmath now consistently defaults to the NIST system.- parse_string_unsafe() deprecated
Use
bitmath.parse_string()withstrict=Falseinstead. The old name still works but emits aDeprecationWarning.- bitmath.integrations removed
The
argparse,click, andprogressbarintegrations have been removed from the package. Copy-paste replacements are provided in the new Integration Examples documentation chapter. No changes to calling code are required — just a local copy of the relevant snippet.- Byte and Bit display names
ByteandBitnow display asBandbrespectively, matching the abbreviated style of every other unit. Code that compares formatted strings (e.g."{unit}"in a format template or the output ofstr()/repr()) against the literal words"Byte"or"Bit"will need to be updated. The class names themselves are unchanged.- query_device_capacity() on macOS
bitmath.query_device_capacity()now raisesNotImplementedErroron macOS. System Integrity Protection (SIP) blocks raw block device access even for root, making the previous ioctl path unreliable. Usebitmath.query_capacity()instead.- Build and install
setup.pyandsetup.py.inare gone. Installation ispip install bitmath. Source builds usepython -m build.
10.2.2. Library Improvements
The core API is unchanged — every bitmath object you created before still works exactly the same way. What 2.0.0 adds on top of that:
- Full NIST unit coverage
The four largest NIST prefix units —
ZiB,YiB,Zib, andYib— are now first-class bitmath types. All constants (NIST_PREFIXES, NIST_STEPS, ALL_UNIT_TYPES) reflect reality.- f-string and format() support
bitmath objects now implement the Python format protocol (
__format__, PEP 3101). They can be used directly in f-strings with format specs —f"{some_size:.2f}"just works. See Python Format Protocol (f-strings and format()) for the full reference. Credit to Jonathan Eunice for the original concept in PR #76.- bitmath.sum() and built-in sum()
A new
bitmath.sum()function returns a unit-normalized result when summing mixed-type iterables. For uniform collections, the built-insum()now works directly on bitmath sequences without astart=argument.- Thread-safe context manager
The
bitmath.format()context manager previously mutated module-level globals, making it unsafe under concurrent access. It now usesthreading.localwith proper save/restore semantics, including correct nesting behavior. Closes issue #83.- best_prefix() bit-family fix
bitmath.best_prefix()incorrectly converted bit-family units (e.g.Kib) into byte-family units (e.g.KiB). The unit family is now preserved. Closes issue #95.- query_capacity() — recommended volume size API
New
bitmath.query_capacity()returns abitmath.CapacityNamedTuple of(total, used, free)bitmath.Bitmathinstances for any path or mount point. Works cross-platform without elevated privileges. This is the recommended API for “how big is this volume?” queries. Acceptsbestprefix=True(default) to get already human-readable units (e.g.GiB) andsystem=bitmath.SIto opt into decimal prefixes instead of the default NIST binary prefixes. Setbestprefix=Falseto receive rawbitmath.Byteinstances.- Windows device capacity
bitmath.query_device_capacity()now works on Windows viaDeviceIoControl. Open the device asopen(r'\\.\PhysicalDrive0', 'rb')(administrator privileges required). Unsupported platforms raiseNotImplementedError. The newbitmath.SUPPORTED_PLATFORMSconstant lists all platforms where the function is available. Closes issue #52.- query_device_capacity() Linux buffer fix
bitmath.query_device_capacity()on Linux was passing an integer where an ioctl buffer was required, causingOSError: [Errno 14] Bad address. The call now correctly allocates a zero-filled buffer of the proper size viab'\\x00' * struct.calcsize(fmt).- Flexible string parsing
bitmath.parse_string()withstrict=Falseaccepts ambiguous input such as"1g"or"1GB"and resolves it to the most likely unit. When the system cannot be reliably determined, NIST is the tiebreaker. Closes issue #54.- Floor division, modulo, and divmod for capacity math
bitmath objects now implement
__floordiv__(//),__mod__(%), and__divmod__— useful for chunk-and-remainder capacity planning (“how many N-sized chunks fit into this device, and how much is left over?”).bm1 // bm2returns anint(count of whole divisions), mirroring howbm1 / bm2returns a unitless ratio.bm1 % bm2anddivmod(bm1, bm2)return remainders as bitmath objects of the left-hand operand’s type, consistent with every other bitmath arithmetic operator. The identity(a // b) * b + (a % b) == aholds. See Capacity Math: Floor Division and Modulo for worked examples includingbest_prefix()coercion andbitmath.formatcontext-manager integration.
10.2.3. Project Infrastructure
The project infrastructure has been rebuilt to reflect how Python projects are actually maintained in 2026:
- Project Security
GitHub now has branch protection enabled. Releases are signed with the maintainers GPG key.
- Packaging
pyproject.tomlwith a hatchling backend replaces the oldsetup.py/setup.py.intemplate system. The package is PEP 517/PEP 518 compliant.MANIFEST.inis gone; sdist content is declared explicitly inpyproject.toml.- GitHub Actions
CI now runs against Python 3.9 through 3.13 on Ubuntu, macOS, and Windows, with actions pinned to current versions (
checkout@v6,setup-python@v5). Tests run on every pull request, not just pushes.- Security scanning
CodeQL analysis runs on every push to master, every pull request, and on a weekly schedule.
- ReadTheDocs
.readthedocs.yamlis now present and explicit. The RTD build uses Python 3.11 and installssphinx_rtd_themedirectly.- Development workflow
make ciis the single command for a full local build: unique test name check, pycodestyle, flake8, and pytest with coverage.make build,make pypitest, andmake pypireplace the oldmake sdist uploadpattern.- Fedora/EPEL
Expect to see fresh builds in Fedora/EPEL over the coming weeks. Hopefully I can sneak this into EPEL 10, EPEL 9 might be picky since this is a major version change.
10.2.4. Closing Thoughts
bitmath started as a small passion project of mine. A utility for thinking about and clearly expressing file sizes, and that’s still exactly what it is. This 2.0.0 release doesn’t change what the library does. What I’ve done is change the very foundation that it’s built on. The test suite measures in at 311 tests now, basically 100% coverage when you add all the platform-specific checks together. The documentation has been comprehensively reviewed and updated. The packaging is modernized.
It really is a remarkable milestone in project history. I have to give the warmest thanks to all of the users and fans who have written bug reports and submitted pull requests. Especially in the least active years of the project. Most of those PRs and Issues have been integrated into this massive 2.0.0 release.
Thanks for your patience and your participation.
If you’ve been holding off on adopting bitmath because the last release predated your Python version — yeah I totally get it. This place was a dumpster for the last 8 years.
Go on, give it a shot. It really is better than ever.
10.3. bitmath-1.4.0-1
bitmath-1.4.0 was published on 2026-04-16.
10.3.1. Project
Version 1.4.0 is a maintenance release — the final release to support Python 2 era packaging infrastructure. It addresses two long-standing issues and makes no breaking changes.
10.3.2. Changes
Bug Fixes
Fixed packaging:
bitmath.integrationssubpackage was missing from thepackageslist insetup.py.in, causing the argparse, click, and progressbar integrations to be absent from installed distributions. Reported in PR #107.Modernized mock imports in the test suite:
tests/test_progressbar.pyandtests/test_query_device_capacity.pynow preferunittest.mock(stdlib, Python 3.3+) and fall back to the third-partymockpackage. Based on PR #105.
10.4. bitmath-1.3.3-1
bitmath-1.3.3-1 was published on 2018-08-23.
10.4.1. Project
Version 1.3.3 is a minor update primarily released to synchronize versions across platforms. Additionally there are small packaging updates to keep up with changing standards.
Minor bug fixes and documentation tweaks are included as well.
The project now has an official Code of Conduct, as well as issue and pull request templates.
What happened to bitmath 1.3.2? It only ever existed as an idea in source control.
10.4.2. Changes
Bug Fixes
Alexander Kapshuna has submitted several fixes since the last release. Thanks!
Packaging requirements fixes
Python 3 compatibility
Subclassing and Type checking fixes/improvements
Marcus Kazmierczak submitted a fix for some broken documentation links.
And Dawid Gosławski make sure our documentation is accurate.
Thanks to all the bitmath contributors over the years!
10.5. bitmath-1.3.1-1
bitmath-1.3.1-1 was published on 2016-07-17.
10.5.1. Changes
Added Functionality
New function:
bitmath.parse_string_unsafe(), a less strict version ofbitmath.parse_string(). Accepts inputs using non-standard prefix units (such as single-letter, or mis-capitalized units).Inspired by @darkblaze69’s request in #60 “Problems in parse_string”.
10.5.2. Project
Ubuntu
Bitmath is now available for installation via Ubuntu Xenial, Wily, Vivid, Trusty, and Precise PPAs.
Ubuntu builds inspired by @hkraal reporting an installation issue on Ubuntu systems.
Documentation
Cleaned up a lot of broken or re-directing links using output from the Sphinx
make linkcheckcommand.
10.6. bitmath-1.3.0-1
bitmath-1.3.0-1 was published on 2016-01-08.
10.6.1. Changes
Bug Fixes
Closed GitHub Issue #55 “best_prefix for negative values”. Now
bitmath.best_prefix()returns correct prefix units for negative values. Thanks mbdm!
10.7. bitmath-1.2.4-1
bitmath-1.2.4-1 was published on 2015-11-30.
10.7.1. Changes
Added Functionality
New bitmath module function:
bitmath.query_device_capacity(). Createbitmath.Byteinstances representing the capacity of a block device. Support is presently limited to Linux and Mac.The
bitmath.parse_string()function now can parse ‘octet’ based units. Enhancement requested in #53 parse french unit names by walidsa3d.
Bug Fixes
#49 - Fix handling unicode input in the bitmath.parse_string function. Thanks drewbrew!
#50 - Update the
setup.pyscript to be python3.x compat. Thanks ssut!
10.7.2. Documentation
The project documentation is now installed along with the bitmath library in RPM packages.
10.7.3. Project
Fedora/EPEL
Look for separate python3.x and python2.x packages coming soon to Fedora and EPEL. This is happening because of the initiative to update the base Python implementation on Fedora to Python 3.x
10.8. bitmath-1.2.3-1
bitmath-1.2.3-1 was published on 2015-01-03.
10.8.1. Changes
Added Functionality
New utility:
progressbarintegration: bitmath.integrations.BitmathFileTransferSpeed. A more functional file transfer speed widget.
10.8.2. Documentation
The command-line
bitmathtool now has online documentationA full demo of the
argparseandprogressbarintegrations has been written. Additionally, it includes a comprehensive demonstration of the full capabilities of the bitmath library. View it in the Real Life Demos Creating Download Progress Bars example.
10.8.3. Project
Tests
Travis-CI had some issues with installing dependencies for the 3.x build unittests. These were fixed and the build status has returned back to normal.
10.9. bitmath-1.2.0-1
bitmath-1.2.0-1 was published on 2014-12-29.
10.9.1. Changes
Added Functionality
New utility:
argparseintegration: bitmath.BitmathType. Allows you to specify arguments as bitmath types.
10.9.2. Documentation
The command-line
bitmathtool now has a proper manpage
10.9.3. Project
Tests
The command-line
bitmathtool is now properly unittested. Code coverage back to ~100%.
10.10. bitmath-1.1.0-1
bitmath-1.1.0-1 was published on 2014-12-20.
10.10.1. Changes
Added Functionality
New
bitmathcommand-line tool added. Provides CLI access to basic unit conversion functionsNew utility function bitmath.parse_string for parsing a human-readable string into a bitmath object. Patch submitted by new contributor tonycpsu.
10.11. bitmath-1.0.5-1 through 1.0.8-1
bitmath-1.0.8-1 was published on 2014-08-14.
10.11.1. Major Updates
bitmath has a proper documentation website up now on Read the Docs, check it out: bitmath.readthedocs.io
bitmath is now Python 3.x compatible
bitmath is now included in the Extra Packages for Enterprise Linux EPEL6 and EPEL7 repositories (pkg info)
merged 6 pull requests from 3 contributors
10.11.2. Bug Fixes
fixed some math implementation bugs
10.11.3. Changes
Added Functionality
best-prefix guessing: automatic best human-readable unit selection
support for bitwise operations
formatting customization methods (including plural/singular selection)
exposed many more instance attributes (all instance attributes are usable in custom formatting)
a context manager for applying formatting to an entire block of code
utility functions for sizing files and directories
add instance properties equivalent to
instance.to_THING()methods
10.11.4. Project
Tests
Test suite is now implemented using Python virtualenv’s for consistency across across platforms
Test suite now contains 150 unit tests. This is 110 more tests than the previous major release (1.0.4-1)
Test suite now runs on EPEL6 and EPEL7
Code coverage is stable around 95-100%
10.12. bitmath-1.0.4-1
This is the first release of bitmath. bitmath-1.0.4-1 was published on 2014-03-20.
10.12.1. Project
Available via:
Fedora 19
Fedora 20
bitmath had been under development for 12 days when the 1.0.4-1 release was made available.
10.12.2. Debut Functionality
Converting between SI and NIST prefix units (
GiBtokB)Converting between units of the same type (SI to SI, or NIST to NIST)
Basic arithmetic operations (subtracting 42KiB from 50GiB)
Rich comparison operations (
1024 Bytes == 1KiB)Sorting
Useful console and print representations