From 828fd633489d26acb8458a87161836b354e3908f Mon Sep 17 00:00:00 2001 From: tersec Date: Thu, 30 May 2024 19:08:09 +0000 Subject: [PATCH] rm Miracl and remaining i386 (32-bit) build support (#2250) --- .github/workflows/ci.yml | 56 +------ Makefile | 7 - config.nims | 5 - nimbus/evm/blscurve.nim | 305 +++++++++++++++------------------------ 4 files changed, 119 insertions(+), 254 deletions(-) diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index 6e914fe5d..faecdda6b 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -36,9 +36,6 @@ jobs: - os: linux cpu: amd64 evmc: evmc - #- os: linux - # cpu: i386 - # evmc: evmc - os: macos cpu: amd64 evmc: evmc @@ -48,9 +45,6 @@ jobs: - os: linux cpu: amd64 evmc: nimvm - #- os: linux - # cpu: i386 - # evmc: nimvm - os: windows cpu: amd64 evmc: nimvm @@ -93,12 +87,6 @@ jobs: echo "GOARCH=${GOARCH}" >> $GITHUB_ENV echo "USE_MIRACL=${USE_MIRACL}" >> $GITHUB_ENV - # libminiupnp / natpmp - if [[ '${{ runner.os }}' == 'Linux' && '${{ matrix.target.cpu }}' == 'i386' ]]; then - export CFLAGS="${CFLAGS} -m32 -mno-adx" - echo "CFLAGS=${CFLAGS}" >> $GITHUB_ENV - fi - ncpu='' case '${{ runner.os }}' in 'Linux') @@ -120,26 +108,6 @@ jobs: echo "ENABLE_EVMC=0" >> $GITHUB_ENV fi - - name: Install build dependencies (Linux i386) - if: runner.os == 'Linux' && matrix.target.cpu == 'i386' - run: | - sudo dpkg --add-architecture i386 - sudo apt-fast update -qq - sudo DEBIAN_FRONTEND='noninteractive' apt-fast install \ - --no-install-recommends -yq gcc-multilib g++-multilib \ - libz-dev:i386 libbz2-dev:i386 libssl-dev:i386 libpcre3-dev:i386 - mkdir -p external/bin - cat << EOF > external/bin/gcc - #!/bin/bash - exec $(which gcc) -m32 "\$@" - EOF - cat << EOF > external/bin/g++ - #!/bin/bash - exec $(which g++) -m32 "\$@" - EOF - chmod 755 external/bin/gcc external/bin/g++ - echo '${{ github.workspace }}/external/bin' >> $GITHUB_PATH - - name: Install build dependencies (Macos) # Some home brew modules were reported missing if: runner.os == 'Macos' @@ -155,13 +123,6 @@ jobs: path: rocks-db-cache-${{ matrix.target.cpu }} key: 'rocksdb-v2-${{ matrix.target.os }}-${{ matrix.target.cpu }}' - - name: Build and install rocksdb (Linux i386) - # no librocksdb-dev:i386 - if: runner.os == 'Linux' && matrix.target.cpu == 'i386' - run: | - curl -O -L -s -S https://raw.githubusercontent.com/status-im/nimbus-build-system/master/scripts/build_rocksdb.sh - bash build_rocksdb.sh rocks-db-cache-${{ matrix.target.cpu }} - - name: Install rocksdb (Linux amd64) # mysterious illegal instruction error if we build our own librocksdb if: runner.os == 'Linux' && matrix.target.cpu == 'amd64' @@ -282,17 +243,12 @@ jobs: env CC=gcc make ${DEFAULT_MAKE_FLAGS} build/nimbus --help # CC, GOARCH, and CGO_ENABLED are needed to select correct compiler 32/64 bit - if [[ '${{ matrix.target.cpu }}' == 'i386' ]]; then - # hide CI failures - env CC=gcc GOARCH=${GOARCH} CXX=g++ CGO_ENABLED=1 make ${DEFAULT_MAKE_FLAGS} test || true - else - # pushd vendor/nimbus-eth2 - # env NIMBUSEL_BINARY=../../build/nimbus NIMBUSEL_GENESIS=scripts/nimbusel_genesis.json \ - # ./scripts/launch_local_testnet.sh --nodes=3 --stop-at-epoch=7 \ - # --disable-htop --reuse-binaries --run-nimbus-el --dl-eth2 --verbose --kill-old-processes - # popd - env CC=gcc GOARCH=${GOARCH} CXX=g++ CGO_ENABLED=1 make ${DEFAULT_MAKE_FLAGS} test - fi + # pushd vendor/nimbus-eth2 + # env NIMBUSEL_BINARY=../../build/nimbus NIMBUSEL_GENESIS=scripts/nimbusel_genesis.json \ + # ./scripts/launch_local_testnet.sh --nodes=3 --stop-at-epoch=7 \ + # --disable-htop --reuse-binaries --run-nimbus-el --dl-eth2 --verbose --kill-old-processes + # popd + env CC=gcc GOARCH=${GOARCH} CXX=g++ CGO_ENABLED=1 make ${DEFAULT_MAKE_FLAGS} test - name: Run nimbus-eth1 tests (Macos) if: runner.os == 'Macos' diff --git a/Makefile b/Makefile index fe99887dc..4759126af 100644 --- a/Makefile +++ b/Makefile @@ -158,9 +158,6 @@ all: | $(TOOLS) nimbus # must be included after the default target -include $(BUILD_SYSTEM_DIR)/makefiles/targets.mk -# default: use blst -USE_MIRACL := 0 - # default: use nim native evm ENABLE_EVMC := 0 @@ -182,10 +179,6 @@ ifneq ($(USE_LIBBACKTRACE), 0) deps: | libbacktrace endif -ifneq ($(USE_MIRACL), 0) - NIM_PARAMS += -d:BLS_FORCE_BACKEND=miracl -endif - ifneq ($(ENABLE_EVMC), 0) NIM_PARAMS += -d:evmc_enabled T8N_PARAMS := -d:chronicles_enabled=off diff --git a/config.nims b/config.nims index 1e6cb05fa..e41cfa341 100644 --- a/config.nims +++ b/config.nims @@ -152,11 +152,6 @@ switch("warning", "ObservableStores:off") # Too many false positives for "Warning: method has lock level , but another method has 0 [LockLevel]" switch("warning", "LockLevel:off") -if defined(windows) and defined(i386): - # avoid undefined reference to 'sqrx_mont_384x' when compiling in 32 bit mode - # without actually using __BLST_PORTABLE__ or __BLST_NO_ASM__ - switch("define", "BLS_FORCE_BACKEND:miracl") - # nim-kzg shipping their own blst, nimbus-eth1 too. # disable nim-kzg's blst switch("define", "kzgExternalBlst") diff --git a/nimbus/evm/blscurve.nim b/nimbus/evm/blscurve.nim index c6aeacc99..f72b6e9ff 100644 --- a/nimbus/evm/blscurve.nim +++ b/nimbus/evm/blscurve.nim @@ -1,5 +1,5 @@ # Nimbus -# Copyright (c) 2020-2023 Status Research & Development GmbH +# Copyright (c) 2020-2024 Status Research & Development GmbH # Licensed under either of # * Apache License, version 2.0, ([LICENSE-APACHE](LICENSE-APACHE) or # http://www.apache.org/licenses/LICENSE-2.0) @@ -10,189 +10,128 @@ import blscurve/bls_backend, stint -when BLS_BACKEND == Miracl: - import blscurve/miracl/[common, milagro, hash_to_curve, miracl_min_pubkey_sig_core] - import map_to_curve_g1 - export common - export miracl_min_pubkey_sig_core.subgroupCheck +import blscurve/blst/[blst_lowlevel] - type - BLS_G1* = ECP_BLS12381 - BLS_G2* = ECP2_BLS12381 - BLS_FP* = BIG_384 - BLS_FP2* = FP2_BLS12381 - BLS_SCALAR* = BIG_384 - BLS_FE* = FP_BLS12381 - BLS_FE2* = FP2_BLS12381 - BLS_ACC* = FP12_BLS12381 - BLS_G1P* = BLS_G1 - BLS_G2P* = BLS_G2 +type + BLS_G1* = blst_p1 + BLS_G2* = blst_p2 + BLS_FP* = blst_fp + BLS_FP2* = blst_fp2 + BLS_SCALAR* = blst_scalar + BLS_FE* = blst_fp + BLS_FE2* = blst_fp2 + BLS_ACC* = blst_fp12 + BLS_G1P* = blst_p1_affine + BLS_G2P* = blst_p2_affine - func pack(g: var BLS_G1, x, y: BLS_FP): bool {.inline.} = - discard ECP_BLS12381_set(g.addr, x, y) - let xx = x.nres - let yy = y.nres - isOnCurve(xx, yy) +func fromBytes*(ret: var BLS_SCALAR, raw: openArray[byte]): bool = + const L = 32 + if raw.len < L: + return false + let pa = cast[ptr array[L, byte]](raw[0].unsafeAddr) + blst_scalar_from_bendian(ret, pa[]) + true - func unpack(g: BLS_G1, x, y: var BLS_FP): bool {.inline.} = - discard g.get(x, y) - true +func fromBytes(ret: var BLS_FP, raw: openArray[byte]): bool = + const L = 48 + if raw.len < L: + return false + let pa = cast[ptr array[L, byte]](raw[0].unsafeAddr) + blst_fp_from_bendian(ret, pa[]) + true - func pack(g: var BLS_G2, x0, x1, y0, y1: BLS_FP): bool = - var x, y: BLS_FP2 - x.fromBigs(x0, x1) - y.fromBigs(y0, y1) - discard ECP2_BLS12381_set(g.addr, x.addr, y.addr) - isOnCurve(x, y) +func toBytes(fp: BLS_FP, output: var openArray[byte]): bool = + const L = 48 + if output.len < L: + return false + let pa = cast[ptr array[L, byte]](output[0].unsafeAddr) + blst_bendian_from_fp(pa[], fp) + true - func unpack(g: BLS_G2, x0, x1, y0, y1: var BLS_FP): bool = - var x, y: BLS_FP2 - result = g.get(x, y) <= 0.cint - FP_BLS12381_redc(x0, addr x.a) - FP_BLS12381_redc(x1, addr x.b) - FP_BLS12381_redc(y0, addr y.a) - FP_BLS12381_redc(y1, addr y.b) +func pack(g: var BLS_G1, x, y: BLS_FP): bool = + let src = blst_p1_affine(x: x, y: y) + blst_p1_from_affine(g, src) + blst_p1_on_curve(g).int == 1 - func mapFPToG1*(fp: BLS_FE): BLS_G1 {.inline.} = - mapToCurveG1(fp) +func unpack(g: BLS_G1, x, y: var BLS_FP): bool = + var dst: blst_p1_affine + blst_p1_to_affine(dst, g) + x = dst.x + y = dst.y + true - func mapFPToG2*(fp: BLS_FE2): BLS_G2 {.inline.} = - result = mapToCurveG2(fp) - result.clearCofactor() +func pack(g: var BLS_G2, x0, x1, y0, y1: BLS_FP): bool = + let src = blst_p2_affine(x: blst_fp2(fp: [x0, x1]), y: blst_fp2(fp: [y0, y1])) + blst_p2_from_affine(g, src) + blst_p2_on_curve(g).int == 1 - func millerLoop*(g1: BLS_G1, g2: BLS_G2): BLS_ACC {.inline.} = - PAIR_BLS12381_ate(result.addr, g2.unsafeAddr, g1.unsafeAddr) +func unpack(g: BLS_G2, x0, x1, y0, y1: var BLS_FP): bool = + var dst: blst_p2_affine + blst_p2_to_affine(dst, g) + x0 = dst.x.fp[0] + x1 = dst.x.fp[1] + y0 = dst.y.fp[0] + y1 = dst.y.fp[1] + true - proc mul*(a: var BLS_ACC, b: BLS_ACC) {.inline.} = - FP12_BLS12381_mul(a.addr, b.unsafeAddr) +func nbits(s: BLS_SCALAR): uint = + var k = sizeof(s.l) - 1 + while k >= 0 and s.l[k] == 0: dec k + if k < 0: return 0 + var + bts = k shl 3 + c = s.l[k] - func check*(x: BLS_ACC): bool {.inline.} = - PAIR_BLS12381_fexp(x.unsafeAddr) - FP12_BLS12381_isunity(x.unsafeAddr).int == 1 + while c != 0: + c = c shr 1 + inc bts -else: - import blscurve/blst/[blst_lowlevel] + result = bts.uint - type - BLS_G1* = blst_p1 - BLS_G2* = blst_p2 - BLS_FP* = blst_fp - BLS_FP2* = blst_fp2 - BLS_SCALAR* = blst_scalar - BLS_FE* = blst_fp - BLS_FE2* = blst_fp2 - BLS_ACC* = blst_fp12 - BLS_G1P* = blst_p1_affine - BLS_G2P* = blst_p2_affine +func add*(a: var BLS_G1, b: BLS_G1) {.inline.} = + blst_p1_add_or_double(a, a, b) - func fromBytes*(ret: var BLS_SCALAR, raw: openArray[byte]): bool = - const L = 32 - if raw.len < L: - return false - let pa = cast[ptr array[L, byte]](raw[0].unsafeAddr) - blst_scalar_from_bendian(ret, pa[]) - true +func mul*(a: var BLS_G1, b: BLS_SCALAR) {.inline.} = + blst_p1_mult(a, a, b, b.nbits) - func fromBytes(ret: var BLS_FP, raw: openArray[byte]): bool = - const L = 48 - if raw.len < L: - return false - let pa = cast[ptr array[L, byte]](raw[0].unsafeAddr) - blst_fp_from_bendian(ret, pa[]) - true +func add*(a: var BLS_G2, b: BLS_G2) {.inline.} = + blst_p2_add_or_double(a, a, b) - func toBytes(fp: BLS_FP, output: var openArray[byte]): bool = - const L = 48 - if output.len < L: - return false - let pa = cast[ptr array[L, byte]](output[0].unsafeAddr) - blst_bendian_from_fp(pa[], fp) - true +func mul*(a: var BLS_G2, b: BLS_SCALAR) {.inline.} = + blst_p2_mult(a, a, b, b.nbits) - func pack(g: var BLS_G1, x, y: BLS_FP): bool = - let src = blst_p1_affine(x: x, y: y) - blst_p1_from_affine(g, src) - blst_p1_on_curve(g).int == 1 +func mapFPToG1*(fp: BLS_FE): BLS_G1 {.inline.} = + let z: ptr blst_fp = nil + blst_map_to_g1(result, fp, z[]) - func unpack(g: BLS_G1, x, y: var BLS_FP): bool = - var dst: blst_p1_affine - blst_p1_to_affine(dst, g) - x = dst.x - y = dst.y - true +func mapFPToG2*(fp: BLS_FE2): BLS_G2 {.inline.} = + let z: ptr blst_fp2 = nil + blst_map_to_g2(result, fp, z[]) - func pack(g: var BLS_G2, x0, x1, y0, y1: BLS_FP): bool = - let src = blst_p2_affine(x: blst_fp2(fp: [x0, x1]), y: blst_fp2(fp: [y0, y1])) - blst_p2_from_affine(g, src) - blst_p2_on_curve(g).int == 1 +func pack(g: var BLS_G1P, x, y: BLS_FP): bool = + g = blst_p1_affine(x: x, y: y) + blst_p1_affine_on_curve(g).int == 1 - func unpack(g: BLS_G2, x0, x1, y0, y1: var BLS_FP): bool = - var dst: blst_p2_affine - blst_p2_to_affine(dst, g) - x0 = dst.x.fp[0] - x1 = dst.x.fp[1] - y0 = dst.y.fp[0] - y1 = dst.y.fp[1] - true +func pack(g: var BLS_G2P, x0, x1, y0, y1: BLS_FP): bool = + g = blst_p2_affine(x: blst_fp2(fp: [x0, x1]), y: blst_fp2(fp: [y0, y1])) + blst_p2_affine_on_curve(g).int == 1 - func nbits(s: BLS_SCALAR): uint = - var k = sizeof(s.l) - 1 - while k >= 0 and s.l[k] == 0: dec k - if k < 0: return 0 - var - bts = k shl 3 - c = s.l[k] +func subgroupCheck*(P: BLS_G1P): bool {.inline.} = + blst_p1_affine_in_g1(P).int == 1 - while c != 0: - c = c shr 1 - inc bts +func subgroupCheck*(P: BLS_G2P): bool {.inline.} = + blst_p2_affine_in_g2(P).int == 1 - result = bts.uint +func millerLoop*(P: BLS_G1P, Q: BLS_G2P): BLS_ACC {.inline.} = + blst_miller_loop(result, Q, P) - func add*(a: var BLS_G1, b: BLS_G1) {.inline.} = - blst_p1_add_or_double(a, a, b) +proc mul*(a: var BLS_ACC, b: BLS_ACC) {.inline.} = + blst_fp12_mul(a, a, b) - func mul*(a: var BLS_G1, b: BLS_SCALAR) {.inline.} = - blst_p1_mult(a, a, b, b.nbits) - - func add*(a: var BLS_G2, b: BLS_G2) {.inline.} = - blst_p2_add_or_double(a, a, b) - - func mul*(a: var BLS_G2, b: BLS_SCALAR) {.inline.} = - blst_p2_mult(a, a, b, b.nbits) - - func mapFPToG1*(fp: BLS_FE): BLS_G1 {.inline.} = - let z: ptr blst_fp = nil - blst_map_to_g1(result, fp, z[]) - - func mapFPToG2*(fp: BLS_FE2): BLS_G2 {.inline.} = - let z: ptr blst_fp2 = nil - blst_map_to_g2(result, fp, z[]) - - func pack(g: var BLS_G1P, x, y: BLS_FP): bool = - g = blst_p1_affine(x: x, y: y) - blst_p1_affine_on_curve(g).int == 1 - - func pack(g: var BLS_G2P, x0, x1, y0, y1: BLS_FP): bool = - g = blst_p2_affine(x: blst_fp2(fp: [x0, x1]), y: blst_fp2(fp: [y0, y1])) - blst_p2_affine_on_curve(g).int == 1 - - func subgroupCheck*(P: BLS_G1P): bool {.inline.} = - blst_p1_affine_in_g1(P).int == 1 - - func subgroupCheck*(P: BLS_G2P): bool {.inline.} = - blst_p2_affine_in_g2(P).int == 1 - - func millerLoop*(P: BLS_G1P, Q: BLS_G2P): BLS_ACC {.inline.} = - blst_miller_loop(result, Q, P) - - proc mul*(a: var BLS_ACC, b: BLS_ACC) {.inline.} = - blst_fp12_mul(a, a, b) - - func check*(x: BLS_ACC): bool {.inline.} = - var ret: BLS_ACC - ret.blst_final_exp(x) - ret.blst_fp12_is_one().int == 1 +func check*(x: BLS_ACC): bool {.inline.} = + var ret: BLS_ACC + ret.blst_final_exp(x) + ret.blst_fp12_is_one().int == 1 # decodeFieldElement expects 64 byte input with zero top 16 bytes, # returns lower 48 bytes. @@ -207,40 +146,22 @@ func decodeFieldElement*(res: var BLS_FP, input: openArray[byte]): bool = res.fromBytes input.toOpenArray(16, 63) -when BLS_BACKEND == Miracl: - proc decodeFE*(res: var BLS_FE, input: openArray[byte]): bool = - var big: BLS_FP - if not big.decodeFieldElement(input): - return false - res = big.nres() - # fieldModulus > big - BIG_384_comp(FIELD_Modulus, big).int == 1 +func decodeFE*(res: var BLS_FE, input: openArray[byte]): bool = + const + fieldModulus = StUint[512].fromHex "0x1a0111ea397fe69a4b1ba7b6434bacd764774b84f38512bf6730d2a0f6b0f6241eabfffeb153ffffb9feffffffffaaab" + if not res.decodeFieldElement(input): + return false + var z: StUint[512] + z.initFromBytesBE(input) + z < fieldModulus - proc decodeFE*(res: var BLS_FE2, input: openArray[byte]): bool = - if input.len != 128: - return false +func decodeFE*(res: var BLS_FE2, input: openArray[byte]): bool = + if input.len != 128: + return false - if res.a.decodeFE(input.toOpenArray(0, 63)) and - res.b.decodeFE(input.toOpenArray(64, 127)): - result = true - -else: - func decodeFE*(res: var BLS_FE, input: openArray[byte]): bool = - const - fieldModulus = StUint[512].fromHex "0x1a0111ea397fe69a4b1ba7b6434bacd764774b84f38512bf6730d2a0f6b0f6241eabfffeb153ffffb9feffffffffaaab" - if not res.decodeFieldElement(input): - return false - var z: StUint[512] - z.initFromBytesBE(input) - z < fieldModulus - - func decodeFE*(res: var BLS_FE2, input: openArray[byte]): bool = - if input.len != 128: - return false - - if res.fp[0].decodeFE(input.toOpenArray(0, 63)) and - res.fp[1].decodeFE(input.toOpenArray(64, 127)): - result = true + if res.fp[0].decodeFE(input.toOpenArray(0, 63)) and + res.fp[1].decodeFE(input.toOpenArray(64, 127)): + result = true # DecodePoint given encoded (x, y) coordinates in 128 bytes returns a valid G1 Point. func decodePoint*(g: var (BLS_G1 | BLS_G1P), data: openArray[byte]): bool =