DEV Community

Vano Chkheidze
Vano Chkheidze

Posted on

Why I Built a Zero-Dependency secp256k1 Library From Scratch

The Problem
If you've ever tried to do secp256k1 cryptography across multiple platforms — from a server with AVX-512 to an ESP32 microcontroller to a WebAssembly module — you know the pain. Different libraries, different APIs, different dependency trees, different bugs.

I wanted one library that works everywhere, depends on nothing, and covers everything the modern Bitcoin/EVM ecosystem needs.

What UltrafastSecp256k1 Covers
Core: Field/Scalar/Point arithmetic, GLV endomorphism, precomputation, RFC 6979, low-S normalization.

Signatures: ECDSA (sign, verify, recover, batch), Schnorr BIP-340 (sign, verify, batch).

Advanced Protocols: MuSig2 (2-round aggregation), FROST (t-of-n threshold), Adaptor signatures, Pedersen commitments, Multi-scalar multiplication (Strauss/Shamir), ECDH.

Bitcoin: Taproot (BIP-341/342), BIP-32 HD keys, BIP-44 coin derivation, BIP-352 Silent Payments, P2PKH/P2WPKH/P2TR/Base58/Bech32.

Multi-Chain: 27+ coins including ETH (EIP-55 checksums), LTC, DOGE, ZEC, DASH — with a built-in Keccak-256.

Zero dependencies means: SHA-256, SHA-512, HMAC, Keccak-256, RIPEMD-160, Base58Check, Bech32/Bech32m — all implemented from scratch in the library.

Performance Design
Assembly backends for x64 (BMI2/ADX → 3-5× speedup), ARM64 (~5×), and RISC-V. SIMD with AVX2/AVX-512. GPU with CUDA (4.63M kG/s), OpenCL (3.39M kG/s), and ROCm/HIP.

Constant-time operations live in a separate secp256k1::ct namespace — no runtime flag switching, explicit API separation.

9 Platforms, One Codebase
Platform Notes
x86-64 BMI2/ADX assembly, AVX2/AVX-512
ARM64 MUL/UMULH inline asm
RISC-V RV64GC native assembly
ESP32 Xtensa LX7/LX6
STM32 ARM Cortex-M3
WebAssembly Emscripten, ES6 + TypeScript
iOS SPM, CocoaPods, XCFramework
Android NDK r27, Clang 18
GPU CUDA, OpenCL, ROCm/HIP
Try It
MIT licensed. 200+ tests. PRs welcome.

→ github.com/shrec/UltrafastSecp256k1

Top comments (0)