Skip to content

Commit

Permalink
llvm: prepare generalizing inline ASM codegen to LLVM IR
Browse files Browse the repository at this point in the history
  • Loading branch information
mratsim committed Jan 17, 2025
1 parent d1e6001 commit 4d6a35c
Show file tree
Hide file tree
Showing 28 changed files with 53 additions and 33 deletions.
10 changes: 5 additions & 5 deletions constantine/mac/mac_poly1305.nim
Original file line number Diff line number Diff line change
Expand Up @@ -7,13 +7,13 @@
# at your option. This file may not be copied, modified, or distributed except according to those terms.

import
../platforms/[abstractions, views],
../math/arithmetic/bigints,
../math/arithmetic/[limbs, limbs_extmul],
../math/io/io_bigints
constantine/platforms/[abstractions, views],
constantine/math/arithmetic/bigints,
constantine/math/arithmetic/[limbs, limbs_extmul],
constantine/math/io/io_bigints

when UseASM_X86_64:
import ../math/arithmetic/assembly/limbs_asm_modular_x86
import constantine/math_asm/limbs_asm_modular_x86

# No exceptions allowed
{.push raises: [].}
Expand Down
4 changes: 2 additions & 2 deletions constantine/math/arithmetic/finite_fields.nim
Original file line number Diff line number Diff line change
Expand Up @@ -35,9 +35,9 @@ import
./bigints_crandall

when UseASM_X86_64:
import ./assembly/limbs_asm_modular_x86
import constantine/math_asm/limbs_asm_modular_x86
when UseASM_ARM64:
import ./assembly/limbs_asm_modular_arm64
import constantine/math_asm/limbs_asm_modular_arm64

when nimvm:
from constantine/named/deriv/precompute import montyResidue_precompute
Expand Down
4 changes: 2 additions & 2 deletions constantine/math/arithmetic/limbs.nim
Original file line number Diff line number Diff line change
Expand Up @@ -9,9 +9,9 @@
import constantine/platforms/abstractions

when UseASM_X86_32:
import ./assembly/limbs_asm_bigint_x86
import constantine/math_asm/limbs_asm_bigint_x86
when UseASM_ARM64:
import ./assembly/limbs_asm_bigint_arm64
import constantine/math_asm/limbs_asm_bigint_arm64

# ############################################################
#
Expand Down
4 changes: 2 additions & 2 deletions constantine/math/arithmetic/limbs_crandall.nim
Original file line number Diff line number Diff line change
Expand Up @@ -12,8 +12,8 @@ import

when UseASM_X86_32:
import
./assembly/limbs_asm_crandall_x86,
./assembly/limbs_asm_crandall_x86_adx_bmi2
constantine/math_asm/limbs_asm_crandall_x86,
constantine/math_asm/limbs_asm_crandall_x86_adx_bmi2

# No exceptions allowed
{.push raises: [], checks: off.}
Expand Down
6 changes: 3 additions & 3 deletions constantine/math/arithmetic/limbs_extmul.nim
Original file line number Diff line number Diff line change
Expand Up @@ -11,10 +11,10 @@ import
./limbs

when UseASM_X86_64:
import ./assembly/limbs_asm_mul_x86
import ./assembly/limbs_asm_mul_x86_adx_bmi2
import constantine/math_asm/limbs_asm_mul_x86
import constantine/math_asm/limbs_asm_mul_x86_adx_bmi2
when UseASM_ARM64:
import ./assembly/limbs_asm_mul_arm64
import constantine/math_asm/limbs_asm_mul_arm64

# ############################################################
#
Expand Down
12 changes: 6 additions & 6 deletions constantine/math/arithmetic/limbs_montgomery.nim
Original file line number Diff line number Diff line change
Expand Up @@ -12,16 +12,16 @@ import
./limbs, ./limbs_extmul

when UseASM_X86_32:
import ./assembly/limbs_asm_redc_mont_x86
import constantine/math_asm/limbs_asm_redc_mont_x86
when UseASM_X86_64:
import
./assembly/limbs_asm_mul_mont_x86,
./assembly/limbs_asm_mul_mont_x86_adx_bmi2,
./assembly/limbs_asm_redc_mont_x86_adx_bmi2
constantine/math_asm/limbs_asm_mul_mont_x86,
constantine/math_asm/limbs_asm_mul_mont_x86_adx_bmi2,
constantine/math_asm/limbs_asm_redc_mont_x86_adx_bmi2
when UseASM_ARM64:
import
./assembly/limbs_asm_mul_mont_arm64,
./assembly/limbs_asm_redc_mont_arm64
constantine/math_asm/limbs_asm_mul_mont_arm64,
constantine/math_asm/limbs_asm_redc_mont_arm64

# ############################################################
#
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,7 @@ import
constantine/platforms/abstractions,
constantine/named/algebras,
constantine/math/arithmetic,
constantine/math/arithmetic/assembly/[
constantine/math_asm/[
limbs_asm_mul_x86_adx_bmi2,
limbs_asm_mul_mont_x86_adx_bmi2,
limbs_asm_redc_mont_x86_adx_bmi2
Expand Down
2 changes: 1 addition & 1 deletion constantine/math/extension_fields/towers.nim
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,7 @@ export Fp

when UseASM_X86_64:
import
./assembly/fp2_asm_x86_adx_bmi2
constantine/math_asm/fp2_asm_x86_adx_bmi2

# Note: to avoid burdening the Nim compiler, we rely on generic extension
# to complain if the base field procedures don't exist
Expand Down
28 changes: 28 additions & 0 deletions constantine/math_asm/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
# Assembly code generator for mathematical primitives

This folder holds code generators for inline assembly in Nim and LLVM IR.

Inline assembly is necessary for security, ensure constant-time from a high-level language, and performance as certain instructions cannot be emitted by a compiler (ADOX/ADCX) despite offering a large performance advantage (up to 70% for ADOX/ADCX).

Even when using LLVM IR and in the case where all instructions can be emitted (ARM64),
and the number of compute instructions between inline assembly and LLVM IR is the same
stack usage might be significantly worse due to bad register allocation and regular stack spill.

For example on ARM64, with LLVM IR that mirrors inline assembly we get the following
breakdown on 6 limbs (CodeGenLevelDefault):
- inline ASM vs pure LLVM IR
- 64 bytes stack vs 368
- 4 stp vs 23
- 10 ldp vs 35
- 6 ldr vs 61
- 6 str vs 43
- 6 mov vs 24
- 78 mul vs 78
- 72 umulh vs 72
- 17 adds vs 17
- 103 adcs vs 103
- 23 adc vs 12 -> the ADC have become cset to save the carry/borrow flag in register
- 6 cmn vs 6
- 0 cset vs 11

And generating single instruction in LLVM inline assembly doesn't solve register spilling to the stack.
Original file line number Diff line number Diff line change
Expand Up @@ -78,10 +78,6 @@ macro ccopy_gen[N: static int](a_PIR: var Limbs[N], b_PIR: Limbs[N], ctl: Secret
# Codegen
result.add ctx.generate()

debugEcho "======Transfo====="
debugEcho getImplTransformed(result).repr()
debugEcho "======"

func ccopy_asm*(a: var Limbs, b: Limbs, ctl: SecretBool) =
## Constant-time conditional copy
## If ctl is true: b is copied into a
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -236,9 +236,6 @@ macro mulMont_CIOS_sparebit_gen[N: static int](
ctx.str t[i], r[i]

result.add ctx.generate()
debugEcho "======Transfo====="
debugEcho getImplTransformed(result).repr()
debugEcho "======"

func mulMont_CIOS_sparebit_asm*(r: var Limbs, a, b, M: Limbs, m0ninv: BaseType, lazyReduce: static bool = false) =
## Constant-time Montgomery multiplication
Expand Down Expand Up @@ -412,7 +409,6 @@ macro sumprodMont_CIOS_spare2bits_gen[N, K: static int](
ctx.mulhiadd_cio(t[j], m, M[j], t[j])
ctx.mulhiadd_ci(t[N-1], m, M[N-1], t[N-1])


if lazyReduce:
for i in 0 ..< N:
ctx.str t[i], r[i]
Expand Down
File renamed without changes.
2 changes: 1 addition & 1 deletion constantine/platforms/isa_x86/macro_assembler_x86.nim
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@
# * Apache v2 license (license terms in the root directory or at http://www.apache.org/licenses/LICENSE-2.0).
# at your option. This file may not be copied, modified, or distributed except according to those terms.

import ../config
import constantine/platforms/config

when UseAsmSyntaxIntel:
# We need Intel syntax.
Expand Down
2 changes: 1 addition & 1 deletion constantine/platforms/isa_x86/macro_assembler_x86_att.nim
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@

import
std/[macros, strutils, sets, hashes, algorithm, sequtils, enumutils],
../[config, bithacks]
constantine/platforms/[config, bithacks]

# A compile-time inline assembler

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@

import
std/[macros, strutils, sets, hashes, algorithm, sequtils, enumutils],
../[config, bithacks]
constantine/platforms/[config, bithacks]

# A compile-time inline assembler

Expand Down

0 comments on commit 4d6a35c

Please sign in to comment.