Skip to content
Merged
Show file tree
Hide file tree
Changes from 2 commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
32 changes: 28 additions & 4 deletions .github/workflows/ci.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,9 @@ jobs:
- stable
- beta
- 1.88.0 # MSRV
limb_size:
- limb31
- limb62
steps:
- uses: actions/checkout@v6
- uses: IronCoreLabs/rust-toolchain@v1
Expand All @@ -24,6 +27,7 @@ jobs:
- uses: actions-rs/cargo@v1
with:
command: check
args: --no-default-features --features ${{ matrix.limb_size }}

build_linux:
name: (Linux) Builds
Expand All @@ -34,6 +38,13 @@ jobs:
- aarch64-linux-android # Android x64
- x86_64-unknown-linux-musl # Alpine Linux x86_64
- wasm32-unknown-unknown
limb_size:
- limb31
- limb62
exclude:
# WASM requires 31-bit limbs (no 64-bit integers in WASM32)
- target: wasm32-unknown-unknown
limb_size: limb62
steps:
- uses: actions/checkout@v6
- uses: IronCoreLabs/rust-toolchain@v1
Expand All @@ -43,7 +54,7 @@ jobs:
with:
use-cross: true
command: build
args: --release --target=${{ matrix.target }}
args: --release --target=${{ matrix.target }} --no-default-features --features ${{ matrix.limb_size }}

build_macos:
name: (OS X) Builds
Expand All @@ -53,6 +64,9 @@ jobs:
target:
- aarch64-apple-ios
- x86_64-apple-darwin # 64-bit OSX
limb_size:
- limb31
- limb62
steps:
- uses: actions/checkout@v6
- uses: IronCoreLabs/rust-toolchain@v1
Expand All @@ -62,7 +76,7 @@ jobs:
with:
use-cross: true
command: build
args: --release --target=${{ matrix.target }}
args: --release --target=${{ matrix.target }} --no-default-features --features ${{ matrix.limb_size }}

build_win:
name: (Windows) Builds
Expand All @@ -71,6 +85,9 @@ jobs:
matrix:
target:
- x86_64-pc-windows-msvc
limb_size:
- limb31
- limb62
steps:
- uses: actions/checkout@v6
- uses: IronCoreLabs/rust-toolchain@v1
Expand All @@ -79,7 +96,7 @@ jobs:
- uses: actions-rs/cargo@v1
with:
command: build
args: --release --target=${{ matrix.target }}
args: --release --target=${{ matrix.target }} --no-default-features --features ${{ matrix.limb_size }}

test:
name: Test Suite
Expand All @@ -89,6 +106,9 @@ jobs:
rust_version:
- stable
- 1.88.0
limb_size:
- limb31
- limb62
steps:
- uses: actions/checkout@v6
- uses: IronCoreLabs/rust-toolchain@v1
Expand All @@ -97,6 +117,7 @@ jobs:
- uses: actions-rs/cargo@v1
with:
command: test
args: --no-default-features --features ${{ matrix.limb_size }}

bench_build:
name: Bench Compile
Expand All @@ -105,12 +126,15 @@ jobs:
matrix:
rust_version:
- stable
limb_size:
- limb31
- limb62
steps:
- uses: actions/checkout@v6
- uses: IronCoreLabs/rust-toolchain@v1
with:
toolchain: ${{ matrix.rust_version }}
- run: cargo bench --no-run
- run: cargo bench --no-run --no-default-features --features ${{ matrix.limb_size }}

fmt:
name: Rustfmt
Expand Down
9 changes: 8 additions & 1 deletion CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,5 +1,13 @@
# Changelog

## 0.12.0

- **BREAKING**: Default limb size changed from 31-bit to 62-bit for ~1.5-2x performance improvement on 64-bit platforms
- For WASM or 32-bit platforms, use: `gridiron = { version = "0.12", default-features = false, features = ["limb31"] }`
- API is unchanged - this is purely a compile-time change

- Update MSRV to 1.88.0

## 0.11.0

- [[#57]](https://github.com/IronCoreLabs/gridiron/pull/57) - Update rand to 0.9
Expand All @@ -8,7 +16,6 @@

- [[#59]](https://github.com/IronCoreLabs/gridiron/pull/59) - Update to criterion 0.6 (Test only change)


## 0.10.0

- [[#52]](https://github.com/IronCoreLabs/gridiron/pull/52)
Expand Down
5 changes: 4 additions & 1 deletion Cargo.toml
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
[package]
name = "gridiron"
version = "0.11.0"
version = "0.12.0"
edition = "2024"
authors = ["IronCore Labs <code at ironcorelabs.com>"]
repository = "https://github.com/IronCoreLabs/gridiron"
Expand Down Expand Up @@ -28,6 +28,9 @@ rand = "0.9"
criterion = { version = "0.8", default-features = false }

[features]
default = ["limb62"]
limb31 = []
limb62 = []
unstable = []

[profile.bench]
Expand Down
67 changes: 61 additions & 6 deletions README.md
Original file line number Diff line number Diff line change
@@ -1,13 +1,66 @@
Gridiron [![](https://img.shields.io/crates/v/gridiron.svg)](https://crates.io/crates/gridiron) [![](https://docs.rs/gridiron/badge.svg)](https://docs.rs/gridiron) ![Gridiron](https://github.com/IronCoreLabs/gridiron/workflows/Gridiron/badge.svg)
====================
# Gridiron [![crates](https://img.shields.io/crates/v/gridiron.svg)](https://crates.io/crates/gridiron) [![docs](https://docs.rs/gridiron/badge.svg)](https://docs.rs/gridiron) ![Gridiron](https://github.com/IronCoreLabs/gridiron/workflows/Gridiron/badge.svg)

To use this library, you can either use one of the provided finite fields, or you can call the macro to create your own. The two that are included are:

* `fp_480::Fp480`
* `fp_256::Fp256`

These were created like so:
## Macro Invocation Generation

In order to call the `fp31` or `fp62` macros you'll need to do some math based on your large number. We've provided a script in [scripts](./scripts/README.md) that will help you generate those values correctly. Note that the generated module comes with all the tests to ensure the math works correctly.

## Performance: Limb Size Selection

Gridiron supports two internal representations via Cargo feature flags:

* **62-bit limbs (default)**: ~1.5-2x faster on 64-bit platforms, not compatible with WASM or 32-bit platforms
* **31-bit limbs**: WASM-compatible, works on all platforms (32-bit and 64-bit)

### Usage

**Default (62-bit limbs)** - 64-bit platforms only:

```toml
[dependencies]
gridiron = "0.12"
```

**WASM/32-bit compatible (31-bit limbs)**:

```toml
[dependencies]
gridiron = { version = "0.12", default-features = false, features = ["limb31"] }
```

### Platform Compatibility

| Platform | 62-bit limbs | 31-bit limbs |
|----------|--------------|--------------|
| 64-bit | ✓ (default, faster) | ✓ |
| WASM32 | ✗ | ✓ |
| 32-bit | ✗ | ✓ |

The API is identical between limb sizes - switching is purely a compile-time performance optimization.

## Creating Custom Fields

To create a custom finite field with your own prime number, use the `scripts/compute_constants.py` utility:

```bash
# For 31-bit limbs (WASM-compatible)
nix-shell -p python3 --run "./scripts/compute_constants.py --limb-size 31 --prime YOUR_PRIME --module my_field --classname MyField --bits 256 --quiet"

# For 62-bit limbs (64-bit platforms only)
nix-shell -p python3 --run "./scripts/compute_constants.py --limb-size 62 --prime YOUR_PRIME --module my_field --classname MyField --bits 256 --quiet"
```

The script will compute all required Montgomery arithmetic constants and output a complete macro invocation ready to paste into your code. See `scripts/README.md` for more details.

### Example

The included fields were created like so:

```rust
// p = 65000549695646603732796438742359905742825358107623003571877145026864184071783
fp31!(
fp_256, // Name of mod
Expand Down Expand Up @@ -46,20 +99,22 @@ These were created like so:
// (-m).inverse_mod(2^31)
2132269737
);

```

To use it, you'll need to import headers for the math operations you want. So, for example:

```rust
use std::ops::Add;
let one = fp_256::Fp256::one();
let two = one + one;
```

All operations provided by the library are constant time (meaning that they are implemented to prevent a timing or memory access pattern side-channel attack from extracting a value that should be kept secret, such as a private key) except:

`Mul<u64>`, `Pow<u64>` - If you need a constant time version of those, you can lift them into an Fp type and use `Mul<Fp>` and `Pow<Fp>`.
`Mul<u64>`, `Pow<u64>` - If you need a constant time version of those, you can lift them into an Fp type and use `Mul<Fp>` and `Pow<Fp>`.
The will be much slower and typically the u64s are not secret values so it's ok for them to be non constant time.

# Code Audit
## Code Audit

NCC Group's [Cryptography Services](https://www.nccgroup.trust/us/our-services/cyber-security/specialist-practices/cryptography-services/) team has conducted an audit of this library - release [0.6.0](https://github.com/IronCoreLabs/gridiron/releases/tag/0.6.0) contains all of the audited code, including updates that were created to resolve issues that were discovered during the audit. The NCC Group audit found that the chosen pairing and elliptic curve are cryptographically sound, and that the Rust implementation is a faithful and correct embodiment of the target protocol. In addition, the audit specifically looked for but did not find any leak of secret information via timing or memory access pattern side-channel attacks.

Expand Down
Loading