js-cuint

Emulates C-style unsigned 32-bit and 64-bit integer arithmetic in JavaScript, giving hashing and bit-twiddling code overflow-safe math without floating-point rounding.

Library
npm
v0.2.2
31stars
MIT License

Repository Health

Pre-computed score based on development activity, maintenance, community, maturity, and trend momentum.How we score it →
23/100Needs Attention
Development Activity0
Maintenance0
Community20
Maturity60
Momentum12

Technical Analysis

AI-assessed by reading the actual repository — architecture, code quality, innovation, and documentation.How we score it →
51/100Fair
Architecture60
Code Quality55
Innovation35
Learning Curve55

cuint fills a gap that existed in JavaScript before native BigInt: it lets code perform unsigned 32-bit and 64-bit integer arithmetic (add, subtract, multiply, divide, shifts, rotations, and bitwise ops) with correct C-style overflow/truncation behavior, rather than JavaScript’s signed, floating-point-backed number semantics. Each integer is represented internally as a set of 16-bit words (two for UINT32, four for UINT64) so every operation stays within the range where JavaScript’s bitwise operators behave predictably.

The library ships as a small UMD module usable from Node (require('cuint')), AMD loaders, or a plain <script> tag in the browser via prebuilt minified files in build/. It has zero runtime dependencies and was written with performance as the explicit design goal, favoring inlined bit manipulation over object allocation in hot paths like multiply() and div(). It’s most commonly pulled in as a dependency of pure-JS hashing implementations (e.g. MurmurHash and xxHash ports) that need 32/64-bit unsigned arithmetic to match the reference C algorithms exactly.

What You Get

  • UINT32 and UINT64 constructors instantiable from low/high bit pairs, a plain number, or a numeric string with a chosen radix
  • Full arithmetic set: add, subtract, multiply, and div (with an overflow-safe long-division algorithm that also exposes the remainder)
  • Bitwise operations: and, or, xor, not, shiftLeft/shiftRight, and rotateLeft/rotateRight, all mutating in place for chaining
  • Comparison helpers (equals/eq, greaterThan/gt, lessThan/lt) and clone() for creating a non-mutated copy before an operation
  • Prebuilt minified UMD bundles in build/ for direct <script> inclusion in the browser, alongside the Node/CommonJS entry point

Common Use Cases

  • Implementing hash functions (MurmurHash, xxHash, FNV-style algorithms) that require exact unsigned 32/64-bit overflow behavior to match their C reference implementations
  • Porting C/C++ checksum, CRC, or bit-manipulation algorithms to JavaScript without rewriting the overflow logic by hand
  • Working with binary protocols or file formats that encode unsigned 32/64-bit fields, where JavaScript’s native signed doubles would misrepresent large values
  • Building low-level numeric utilities in pre-BigInt codebases or environments where BigInt isn’t available or desirable for performance reasons

Under The Hood

Architecture cuint is organized as two parallel, independently implemented modules (lib/uint32.js, lib/uint64.js), each wrapped in its own UMD IIFE that registers as an AMD module, a CommonJS export, or a global depending on the environment; index.js simply re-exports both as UINT32/UINT64. Neither module shares a common base class or arithmetic helper — UINT32 splits a value into two 16-bit words (_low/_high) while UINT64 splits into four (_a00/_a16/_a32/_a48), and every method (add, multiply, div, shift, rotate) reimplements its own word-carry logic for that representation. This is a deliberately flat, dependency-free computation module with no I/O and no external state, but it means a change to the core word-splitting strategy would require parallel edits across both files rather than a single shared implementation.

Tech Stack The runtime has zero dependencies — plain ES5 JavaScript targeting maximum compatibility across Node, AMD loaders, and browsers via the UMD wrapper pattern. The only devDependencies are mocha for testing and a small “minify” package driven by a custom build.js script, wired to run automatically on prepublish to regenerate the minified browser bundles checked into build/. There is no bundler, transpiler, TypeScript, or framework involved anywhere in the toolchain.

Code Quality Test coverage is extensive at the method level: the test/ directory contains a dedicated spec file per operation per type (e.g. UINT32_add-test.js, UINT64_div-test.js, UINT32_shiftLeft-test.js), run via Mocha with Node’s built-in assert. There is no linter configuration, no CI workflow, and no type annotations anywhere in the repo, so quality enforcement relies entirely on the test suite and manual review. Error handling is minimal and targeted only at truly invalid states (division by zero throws explicitly); most other edge cases are left unguarded, consistent with a small, performance-focused utility rather than a defensively-coded library.

What Makes It Unique cuint isn’t algorithmically novel — it’s one of several userland unsigned-integer emulation libraries that predate JavaScript’s native BigInt (which now solves the same overflow-safety problem at the language level). Its niche is being a lightweight, dependency-free building block that several pure-JS hashing library ports (MurmurHash- and xxHash-style implementations) rely on internally for C-compatible 32/64-bit arithmetic, rather than something end users typically reach for directly.

Join founders buildingwith open source

Opinionated takes, migration guides, cost-saving tips, and insights from the open source ecosystem.

Subscribe on Substack
Join 750+ subscribers

Search