Skip to content
enonymous1Public

About

Interactive C++17 console demo for bit manipulation: set, clear, toggle, negate, and shift a 32-bit value while watching its binary representation change, built with CMake, covered by CTest, and shipped as prebuilt binaries for Linux, Windows, and macOS.

Topics

Resources

Stars

1 star

Watchers

1 watching

Forks

Repository files navigation

BitOps

CI License: MIT C++17

Description

BitOps is an interactive C++17 console demo for bit manipulation. Pick an operation from a menu and watch a 32-bit value and its binary representation change: set, clear, and toggle individual bits, negate the whole value, or shift it left and right.

It started as a 2021 classroom program and was modernized in 2026. The bit operations now live in a testable library (bitops_core), the interactive session is a separate, stream-injected component (bitops_app) that can be driven by scripted tests, and every push is checked by CI on Linux, Windows, and macOS.

This is a teaching demo, not a general-purpose library: it works on one 32-bit value, shifts by one place, and has no command-line interface beyond --help, no file I/O, and no network access.

Prerequisites

  • A C++17 compiler: GCC 7+, Clang 5+, or MSVC 2017+ (any compiler with std::from_chars for integers and inline variables)
  • CMake 3.16 or newer
  • Git, to clone the repository

No third-party libraries are required. Tests are dependency-free and run under CTest.

Installation

Prebuilt binaries are available from GitHub Releases, starting with v1.1.0: download the bitops-<platform>.zip for your system, unzip it, and run the binary inside. The binaries are unsigned, so Windows SmartScreen may warn and macOS Gatekeeper may block the first run; on macOS, xattr -d com.apple.quarantine bit_manipulation-macos-arm64 removes the quarantine flag, or build from source below instead.

Or clone the repository and build the Release configuration:

git clone https://github.com/enonymous1/BitOps.git
cd BitOps
cmake -S . -B build -DCMAKE_BUILD_TYPE=Release
cmake --build build

The executable is build/bit_manipulation (on Windows, build\Release\bit_manipulation.exe).

To install it system-wide after building:

cmake --install build

Or build without CMake, directly with a compiler:

g++ -std=c++17 -Wall -Wextra bit_ops.cpp app.cpp main.cpp -o bit_manipulation

Local Development

Running the program

./build/bit_manipulation

./build/bit_manipulation --help prints usage. Unknown arguments are rejected with exit status 2. Exit the session with menu option 7 or Ctrl-D (closed stdin also exits cleanly with status 0).

Running the tests

Configure a Debug build and run CTest:

cmake -S . -B build -DCMAKE_BUILD_TYPE=Debug
cmake --build build
ctest --test-dir build --output-on-failure

There are two test binaries, both dependency-free:

  • bitops_tests — the library: set/clear/toggle, negation, shifts (including bits shifted out), binary rendering, and out-of-range bit indices, which must throw std::out_of_range.
  • bitops_app_tests — the interactive session, driven through string streams: turn-on/toggle/negate/shift flows, invalid and out-of-range input, trailing junk (1abc is rejected, not read as 1), and EOF in the middle of a prompt.

Sanitizer build

An AddressSanitizer + UndefinedBehaviorSanitizer build is also run in CI on Linux. To run it locally:

cmake -S . -B build-asan -DCMAKE_BUILD_TYPE=Debug \
  -DCMAKE_CXX_FLAGS="-fsanitize=address,undefined -fno-omit-frame-pointer"
cmake --build build-asan
ctest --test-dir build-asan --output-on-failure

Formatting

Code follows the style in .clang-format (4-space indent, Allman braces, 100 columns). The config is currently advisory only: it is not enforced in CI, because the available clang-format versions differ across machines and a pinned-version check has not been added yet. See REVIEW.md for the follow-up.

Project layout

  • bit_ops.hpp / bit_ops.cpp — the bitops_core library: pure bit operations on std::uint32_t
  • app.hpp / app.cpp — the bitops_app library: the menu session over injected input/output streams
  • main.cpp — thin entry point: argument handling only, then calls bitops::runApp
  • tests/test_bit_ops.cpp, tests/test_app.cpp — dependency-free tests, run by CTest
  • CMakeLists.txt — C++17 build with per-target warnings (-Wall -Wextra -Wpedantic, /W4 on MSVC)
  • .github/workflows/ci.yml — build + test on Ubuntu, Windows, and macOS, plus a sanitizer job on Linux
  • CHANGELOG.md — release history
  • REVIEW.md — the staff-level review of v1.0.0 and what v1.1.0 changed in response

Adding an operation

  1. Add the pure function to bit_ops.hpp / bit_ops.cpp (validate any index with std::out_of_range, as the indexed operations do).
  2. Add a case in runApp in app.cpp and a line in printMenu.
  3. Add library cases to tests/test_bit_ops.cpp and, if it is interactive, a scripted session to tests/test_app.cpp.

If the menu grows past about eight operations, replace the switch with a data table (id, label, needs-bit flag, function) that renders the menu and dispatches from one source of truth. At seven operations a table is more machinery than the duplication it removes, so the switch stays for now.

Deployment

There is nothing to deploy. BitOps is a local command-line program: no server, no service, no database, no package registry, and no hosted demo.

Releases are the distribution mechanism, driven by the tag-triggered workflow in .github/workflows/release.yml:

  1. Bump the version in CMakeLists.txt and add an entry to CHANGELOG.md.
  2. Push to main and let CI go green on all three operating systems.
  3. Tag the pushed tip and push the tag — after pushing main, not before, because the workflow has to be in the tagged commit to run:
git tag v1.1.0
git push origin v1.1.0

The workflow first checks that the tag matches the version in CMakeLists.txt (a - suffix is allowed for pre-releases, e.g. v1.2.0-rc1) and runs the test suite. It then builds and tests on Ubuntu, Windows, and macOS, stages each platform's binary plus the LICENSE, and creates a GitHub Release with generated notes containing:

  • bitops-linux-x64.zip — bit_manipulation at the zip root
  • bitops-windows-x64.zip — bit_manipulation.exe at the zip root
  • bitops-macos-arm64.zip — bit_manipulation at the zip root
  • SHA256SUMS.txt — SHA-256 checksums for the three zips, verifiable with sha256sum -c SHA256SUMS.txt after downloading them into one directory

Tags with a - suffix are marked as pre-releases. The binaries are unsigned: see the note in Installation about SmartScreen and Gatekeeper. CI itself (.github/workflows/ci.yml) builds and tests every push to main and every pull request, but does not publish anything — only a tag push creates a release.

Sample session

A real terminal capture. Starting from 2021, turning on bit 1 gives 2023:

------------------------Bit Manipulation------------------------
	Current bitField = 2021
	Bits: 00000000000000000000011111100101

	1) Turn on a bit
	2) Turn off a bit
	3) Toggle a bit
	4) Negate bitField
	5) Left shift bitField
	6) Right shift bitField
	7) Exit

	Enter the number of the operation you'd like to perform: 1

	Choose a bit index (0-31): 1
	Turned on bit 1!

	bitField == 2023
	Bits:	00000000000000000000011111100111

------------------------Bit Manipulation------------------------
	Current bitField = 2023
	Bits: 00000000000000000000011111100111

	1) Turn on a bit
	2) Turn off a bit
	3) Toggle a bit
	4) Negate bitField
	5) Left shift bitField
	6) Right shift bitField
	7) Exit

	Enter the number of the operation you'd like to perform: 7

Exiting BitOps.

License

MIT — see LICENSE.

About

Interactive C++17 console demo for bit manipulation: set, clear, toggle, negate, and shift a 32-bit value while watching its binary representation change, built with CMake, covered by CTest, and shipped as prebuilt binaries for Linux, Windows, and macOS.

Topics

Resources

Stars

1 star

Watchers

1 watching

Forks

Releases

Contributors

Languages