Skip to main content
This page is a placeholder. All examples on this page are currently AI-generated and are not correct. This documentation will be completed in the future with accurate, tested examples.

Overview

Address: 0x000000000000000000000000000000000000000e Introduced: Prague (EIP-2537) EIP: EIP-2537 The BLS12-381 G2 Add precompile performs point addition on the BLS12-381 curve’s G2 group. It adds two G2 points together, computing point1 + point2. This operation is essential for BLS signature aggregation and advanced cryptographic protocols requiring operations over extension fields. BLS12-381 provides 128 bits of security (compared to BN254’s 80 bits) and is used in Ethereum 2.0’s consensus layer for validator signature verification.

Gas Cost

Fixed: 800 gas

G2 vs G1

G2 points are defined over the extension field Fp2 (quadratic extension of the base field):
  • G1 points: 128 bytes (64 bytes per coordinate, 2 coordinates)
  • G2 points: 256 bytes (128 bytes per coordinate, 2 coordinates)
  • Field representation: Each G2 coordinate is an Fp2 element (c0 + c1*u)
  • Computational cost: G2 operations are more expensive than G1 due to extension field arithmetic

Input Format

Offset | Length | Description
-------|--------|-------------
0      | 64     | x.c0 (point1 x-coordinate c0 component, big-endian)
64     | 64     | x.c1 (point1 x-coordinate c1 component, big-endian)
128    | 64     | y.c0 (point1 y-coordinate c0 component, big-endian)
192    | 64     | y.c1 (point1 y-coordinate c1 component, big-endian)
256    | 64     | x.c0 (point2 x-coordinate c0 component, big-endian)
320    | 64     | x.c1 (point2 x-coordinate c1 component, big-endian)
384    | 64     | y.c0 (point2 y-coordinate c0 component, big-endian)
448    | 64     | y.c1 (point2 y-coordinate c1 component, big-endian)
Total input length: 512 bytes (256 bytes per G2 point) Each G2 point coordinate is an Fp2 element represented as: c0 + c1*u where u is the extension field element. Points must satisfy the G2 curve equation: y^2 = x^3 + 4(1 + u) over Fp2.

Output Format

Offset | Length | Description
-------|--------|-------------
0      | 64     | x.c0 (result point x-coordinate c0 component, big-endian)
64     | 64     | x.c1 (result point x-coordinate c1 component, big-endian)
128    | 64     | y.c0 (result point y-coordinate c0 component, big-endian)
192    | 64     | y.c1 (result point y-coordinate c1 component, big-endian)
Total output length: 256 bytes

Usage Example

TypeScript

import { execute, PrecompileAddress } from '@tevm/voltaire/precompiles';
import { Hardfork } from '@tevm/voltaire/primitives/Hardfork';

// Add two G2 points (each 256 bytes: 4x 64-byte Fp2 components)
// Point at infinity for both (valid operation: O + O = O)
const point1 = new Uint8Array(256); // All zeros = point at infinity
const point2 = new Uint8Array(256); // All zeros = point at infinity

const input = new Uint8Array(512);
input.set(point1, 0);
input.set(point2, 256);

const result = execute(
  PrecompileAddress.BLS12_G2_ADD,
  input,
  10000n,
  Hardfork.PRAGUE
);

if (result.success) {
  const resultPoint = result.output; // 256 bytes
  const xc0 = result.output.slice(0, 64);
  const xc1 = result.output.slice(64, 128);
  const yc0 = result.output.slice(128, 192);
  const yc1 = result.output.slice(192, 256);
  console.log('Result G2 point:', { xc0, xc1, yc0, yc1 });
  console.log('Gas used:', result.gasUsed); // 800
} else {
  console.error('Error:', result.error);
}

Zig

const std = @import("std");
const precompiles = @import("precompiles");

pub fn main() !void {
    var gpa = std.heap.GeneralPurposeAllocator(.{}){};
    defer _ = gpa.deinit();
    const allocator = gpa.allocator();

    // Create input: two G2 points (512 bytes)
    var input = [_]u8{0} ** 512;
    // ... populate input with G2 point coordinates

    // Execute G2 addition
    const result = try precompiles.bls12_g2_add.execute(
        allocator,
        &input,
        10000
    );
    defer result.deinit(allocator);

    std.debug.print("Gas used: {}\n", .{result.gas_used});
    std.debug.print("Output length: {}\n", .{result.output.len}); // 256
}

Error Conditions

  • Out of gas: gasLimit < 800
  • Invalid input length: input.len != 512
  • Point not on curve: coordinates don’t satisfy G2 curve equation
  • Invalid field element: coordinate component >= field modulus
  • Invalid encoding: malformed Fp2 element representation

Use Cases

  • BLS signature aggregation: Combine multiple G2 signatures
  • Multi-signature schemes: Aggregate public keys or signatures
  • Threshold cryptography: Combine signature shares
  • Proof aggregation: Combine multiple proofs efficiently
  • Ethereum 2.0 consensus: Validator signature operations

Implementation Details

  • Zig: Uses BLST library via crypto module
  • TypeScript: Wraps @noble/curves bls12-381 G2 operations
  • Algorithm: Projective coordinates for efficiency
  • Security: 128-bit security level (vs BN254’s 80-bit)
  • Constant-time: Implementation resistant to timing attacks

Special Cases

  • Point at infinity: All zeros (256 bytes) represents identity element
  • Identity + P: Returns P
  • P + (-P): Returns point at infinity
  • Identity + identity: Returns identity
The point at infinity is represented as 256 bytes of zeros and acts as the identity element for G2 addition.

Extension Field Arithmetic

G2 points use the quadratic extension field Fp2:
  • Field elements: a = a.c0 + a.c1*u where u^2 + 1 = 0
  • Addition: (a + b) = (a.c0 + b.c0) + (a.c1 + b.c1)*u
  • Multiplication: More complex due to extension field rules
  • Encoding: Each component (c0, c1) is 64 bytes big-endian

Gas Comparison

OperationG1 GasG2 GasRatio
Addition5008001.6x
Multiplication12,00045,0003.75x
MSM (per point)~12,000~45,0003.75x
G2 operations are more expensive due to:
  • Extension field arithmetic (Fp2 vs Fp)
  • Larger point representation (256 vs 128 bytes)
  • More complex coordinate operations

Security Considerations

BLS12-381 advantages over BN254:
  • Security level: 128 bits vs 80 bits
  • Future-proof: Resistant to known attacks on pairing curves
  • Standardization: Used in Ethereum 2.0, Zcash, Filecoin
  • Performance: Efficient pairing computation

Performance Notes

  • G2 addition is ~60% more expensive than G1 addition (800 vs 500 gas)
  • Prefer batching operations when possible
  • Consider using MSM for multiple operations with same points
  • G2 operations required for signature verification in BLS schemes