├── Crypto Village 2017 - Implementing an Elliptic Curve.pdf ├── README ├── curve25519-dalek ├── .gitignore ├── .travis.yml ├── Cargo.toml ├── LICENSE ├── README.md ├── fuzz │ ├── .gitignore │ ├── Cargo.toml │ └── fuzzers │ │ └── decaf.rs └── src │ ├── constants.rs │ ├── curve.rs │ ├── decaf.rs │ ├── field.rs │ ├── lib.rs │ ├── scalar.rs │ └── utils.rs ├── curve25519-go ├── const_amd64.h ├── const_amd64.s ├── cswap_amd64.s ├── curve25519.go ├── curve25519_test.go ├── doc.go ├── freeze_amd64.s ├── ladderstep_amd64.s ├── mont25519_amd64.go ├── mul_amd64.s └── square_amd64.s ├── ed25519-dalek ├── .gitignore ├── .travis.yml ├── Cargo.toml ├── README.md ├── TESTVECTORS ├── res │ └── ed25519-malleability.png └── src │ ├── ed25519.rs │ └── lib.rs ├── ed25519-go ├── ed25519.go ├── ed25519_test.go ├── internal │ └── edwards25519 │ │ ├── const.go │ │ └── edwards25519.go └── testdata │ └── sign.input.gz ├── ed25519-gtank ├── LICENSE ├── README ├── doc.go ├── ed25519.go ├── ed25519_test.go └── internal │ ├── group │ ├── const.go │ └── ge.go │ └── radix51 │ ├── const.go │ ├── fe.go │ ├── fe_mul.go │ ├── fe_mul_amd64.go │ ├── fe_mul_amd64.s │ ├── fe_square.go │ ├── fe_square_amd64.go │ ├── fe_square_amd64.s │ ├── fe_test.go │ └── mul.go └── ed25519-supercop ├── amd64-51-30k ├── api.h ├── architectures ├── batch.c ├── choose_t.s ├── consts.s ├── fe25519.h ├── fe25519_add.c ├── fe25519_freeze.s ├── fe25519_getparity.c ├── fe25519_invert.c ├── fe25519_iseq.c ├── fe25519_iszero.c ├── fe25519_mul.s ├── fe25519_neg.c ├── fe25519_nsquare.s ├── fe25519_pack.c ├── fe25519_pow2523.c ├── fe25519_setint.c ├── fe25519_square.s ├── fe25519_sub.c ├── fe25519_unpack.c ├── ge25519.h ├── ge25519_add.c ├── ge25519_add_p1p1.s ├── ge25519_base.c ├── ge25519_base_niels_smalltables.data ├── ge25519_base_slide_multiples.data ├── ge25519_dbl_p1p1.s ├── ge25519_double.c ├── ge25519_double_scalarmult.c ├── ge25519_isneutral.c ├── ge25519_multi_scalarmult.c ├── ge25519_nielsadd2.s ├── ge25519_nielsadd_p1p1.s ├── ge25519_p1p1_to_p2.s ├── ge25519_p1p1_to_p3.s ├── ge25519_p1p1_to_pniels.s ├── ge25519_pack.c ├── ge25519_pnielsadd_p1p1.s ├── ge25519_scalarmult_base.c ├── ge25519_unpackneg.c ├── heap_rootreplaced.s ├── heap_rootreplaced_1limb.s ├── heap_rootreplaced_2limbs.s ├── heap_rootreplaced_3limbs.s ├── hram.c ├── hram.h ├── implementors ├── index_heap.c ├── index_heap.h ├── keypair.c ├── open.c ├── sc25519.h ├── sc25519_add.s ├── sc25519_barrett.s ├── sc25519_from32bytes.c ├── sc25519_from64bytes.c ├── sc25519_from_shortsc.c ├── sc25519_iszero.c ├── sc25519_lt.s ├── sc25519_mul.c ├── sc25519_mul_shortsc.c ├── sc25519_slide.c ├── sc25519_sub_nored.s ├── sc25519_to32bytes.c ├── sc25519_window4.c ├── sign.c └── ull4_mul.s ├── amd64-64-24k ├── api.h ├── architectures ├── batch.c ├── choose_t.s ├── consts.s ├── fe25519.h ├── fe25519_add.s ├── fe25519_freeze.s ├── fe25519_getparity.c ├── fe25519_invert.c ├── fe25519_iseq.c ├── fe25519_iszero.c ├── fe25519_mul.s ├── fe25519_neg.c ├── fe25519_pack.c ├── fe25519_pow2523.c ├── fe25519_setint.c ├── fe25519_square.s ├── fe25519_sub.s ├── fe25519_unpack.c ├── ge25519.h ├── ge25519_add.c ├── ge25519_add_p1p1.s ├── ge25519_base.c ├── ge25519_base_niels.data ├── ge25519_base_niels_smalltables.data ├── ge25519_base_slide_multiples.data ├── ge25519_dbl_p1p1.s ├── ge25519_double.c ├── ge25519_double_scalarmult.c ├── ge25519_isneutral.c ├── ge25519_multi_scalarmult.c ├── ge25519_nielsadd2.s ├── ge25519_nielsadd_p1p1.s ├── ge25519_p1p1_to_p2.s ├── ge25519_p1p1_to_p3.s ├── ge25519_pack.c ├── ge25519_pnielsadd_p1p1.s ├── ge25519_scalarmult_base.c ├── ge25519_unpackneg.c ├── heap_rootreplaced.s ├── heap_rootreplaced_1limb.s ├── heap_rootreplaced_2limbs.s ├── heap_rootreplaced_3limbs.s ├── hram.c ├── hram.h ├── implementors ├── index_heap.c ├── index_heap.h ├── keypair.c ├── open.c ├── sc25519.h ├── sc25519_add.s ├── sc25519_barrett.s ├── sc25519_from32bytes.c ├── sc25519_from64bytes.c ├── sc25519_from_shortsc.c ├── sc25519_iszero.c ├── sc25519_lt.s ├── sc25519_mul.c ├── sc25519_mul_shortsc.c ├── sc25519_slide.c ├── sc25519_sub_nored.s ├── sc25519_to32bytes.c ├── sc25519_window4.c ├── sign.c └── ull4_mul.s ├── checksumbig ├── checksumsmall ├── description ├── designers ├── ref ├── api.h ├── fe25519.c ├── fe25519.h ├── ge25519.c ├── ge25519.h ├── ge25519_base.data ├── implementors ├── keypair.c ├── open.c ├── sc25519.c ├── sc25519.h └── sign.c └── ref10 ├── Makefile ├── README ├── api.h ├── base.h ├── base.py ├── base2.h ├── base2.py ├── d.h ├── d.py ├── d2.h ├── d2.py ├── fe.h ├── fe_0.c ├── fe_1.c ├── fe_add.c ├── fe_cmov.c ├── fe_copy.c ├── fe_frombytes.c ├── fe_invert.c ├── fe_isnegative.c ├── fe_isnonzero.c ├── fe_mul.c ├── fe_neg.c ├── fe_pow22523.c ├── fe_sq.c ├── fe_sq2.c ├── fe_sub.c ├── fe_tobytes.c ├── ge.h ├── ge_add.c ├── ge_add.h ├── ge_add.q ├── ge_double_scalarmult.c ├── ge_frombytes.c ├── ge_madd.c ├── ge_madd.h ├── ge_madd.q ├── ge_msub.c ├── ge_msub.h ├── ge_msub.q ├── ge_p1p1_to_p2.c ├── ge_p1p1_to_p3.c ├── ge_p2_0.c ├── ge_p2_dbl.c ├── ge_p2_dbl.h ├── ge_p2_dbl.q ├── ge_p3_0.c ├── ge_p3_dbl.c ├── ge_p3_to_cached.c ├── ge_p3_to_p2.c ├── ge_p3_tobytes.c ├── ge_precomp_0.c ├── ge_scalarmult_base.c ├── ge_sub.c ├── ge_sub.h ├── ge_sub.q ├── ge_tobytes.c ├── keypair.c ├── open.c ├── pow22523.h ├── pow22523.q ├── pow225521.h ├── pow225521.q ├── q2h.sh ├── sc.h ├── sc_muladd.c ├── sc_reduce.c ├── sign.c ├── sqrtm1.h └── sqrtm1.py /Crypto Village 2017 - Implementing an Elliptic Curve.pdf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/gtank/defcon25_crypto_village/4c0bc99e9cb667644ea5a3b3085ae3a371cbc355/Crypto Village 2017 - Implementing an Elliptic Curve.pdf -------------------------------------------------------------------------------- /README: -------------------------------------------------------------------------------- 1 | This is all of the code we'll be looking at. 2 | 3 | Current as a July 25 2017. 4 | Dear future: this is NOT a canonical source for any of this code. 5 | -------------------------------------------------------------------------------- /curve25519-dalek/.gitignore: -------------------------------------------------------------------------------- 1 | target 2 | Cargo.lock 3 | 4 | *~ 5 | \#* 6 | .\#* 7 | *.swp 8 | *.orig 9 | *.bak 10 | 11 | *.s 12 | -------------------------------------------------------------------------------- /curve25519-dalek/.travis.yml: -------------------------------------------------------------------------------- 1 | language: rust 2 | 3 | rust: 4 | - stable 5 | - beta 6 | - nightly 7 | 8 | env: 9 | - TEST_COMMAND=test EXTRA_FLAGS='' FEATURES='yolocrypto' 10 | - TEST_COMMAND=test EXTRA_FLAGS='' FEATURES='yolocrypto serde' 11 | - TEST_COMMAND=test EXTRA_FLAGS='' FEATURES='yolocrypto nightly' 12 | - TEST_COMMAND=bench EXTRA_FLAGS='' FEATURES='yolocrypto bench' 13 | - TEST_COMMAND=bench EXTRA_FLAGS='' FEATURES='yolocrypto nightly bench' 14 | - TEST_COMMAND=build EXTRA_FLAGS=--no-default-features FEATURES='' 15 | 16 | matrix: 17 | exclude: 18 | # We can probably remove this, as we reasonably expect dalek to work on 19 | # stable and beta, but currently we require "test" feature in order to 20 | # run benchmarks, which causes dalek not to build on stable. See 21 | # https://github.com/isislovecruft/curve25519-dalek/pull/38#issuecomment-286027562 22 | - rust: stable 23 | env: TEST_COMMAND=bench EXTRA_FLAGS='' FEATURES='yolocrypto bench' 24 | - rust: beta 25 | env: TEST_COMMAND=bench EXTRA_FLAGS='' FEATURES='yolocrypto bench' 26 | - rust: stable 27 | env: TEST_COMMAND=bench EXTRA_FLAGS='' FEATURES='yolocrypto nightly bench' 28 | - rust: beta 29 | env: TEST_COMMAND=bench EXTRA_FLAGS='' FEATURES='yolocrypto nightly bench' 30 | # Test nightly features, such as radix_51, only on nightly. 31 | - rust: stable 32 | env: TEST_COMMAND=test EXTRA_FLAGS='' FEATURES='yolocrypto nightly' 33 | - rust: beta 34 | env: TEST_COMMAND=test EXTRA_FLAGS='' FEATURES='yolocrypto nightly' 35 | # Test no_std only on nightly. 36 | - rust: stable 37 | env: TEST_COMMAND=build EXTRA_FLAGS=--no-default-features FEATURES='' 38 | - rust: beta 39 | env: TEST_COMMAND=build EXTRA_FLAGS=--no-default-features FEATURES='' 40 | - rust: nightly 41 | env: TEST_COMMAND=build EXTRA_FLAGS=--no-default-features FEATURES='alloc' 42 | 43 | script: 44 | - cargo $TEST_COMMAND --features="$FEATURES" $EXTRA_FLAGS 45 | -------------------------------------------------------------------------------- /curve25519-dalek/Cargo.toml: -------------------------------------------------------------------------------- 1 | [package] 2 | name = "curve25519-dalek" 3 | version = "0.9.2" 4 | authors = ["Isis Lovecruft ", 5 | "Henry de Valence "] 6 | readme = "README.md" 7 | license = "CC0-1.0" 8 | repository = "https://github.com/isislovecruft/curve25519-dalek" 9 | homepage = "https://code.ciph.re/isis/curve25519-dalek" 10 | documentation = "https://docs.rs/curve25519-dalek" 11 | categories = ["cryptography", "no-std"] 12 | keywords = ["cryptography", "curve25519", "elliptic", "curve", "ECC"] 13 | description = "A low-level cryptographic library for point, group, field, and scalar operations on a curve isomorphic to the twisted Edwards curve defined by -x²+y² = 1 - 121665/121666 x²y² over GF(2²⁵⁵ - 19)." 14 | exclude = [ 15 | ".gitignore" 16 | ] 17 | 18 | [badges] 19 | travis-ci = { repository = "isislovecruft/curve25519-dalek", branch = "master"} 20 | 21 | [dependencies.serde] 22 | version = "1.0" 23 | optional = true 24 | 25 | [dependencies.arrayref] 26 | version = "0.3.3" 27 | 28 | [dependencies.rand] 29 | optional = true 30 | version = "0.3" 31 | 32 | [dependencies.digest] 33 | version = "0.6" 34 | 35 | [dependencies.subtle] 36 | version = "^0.1" 37 | default-features = false 38 | 39 | [dependencies.generic-array] 40 | # same version that digest depends on 41 | version = "^0.8" 42 | 43 | [dev-dependencies.sha2] 44 | version = "0.6" 45 | 46 | [dev-dependencies.serde_cbor] 47 | version = "0.6" 48 | 49 | [features] 50 | nightly = ["radix_51"] 51 | default = ["std"] 52 | std = ["rand", "subtle/std"] 53 | alloc = [] 54 | yolocrypto = [] 55 | bench = [] 56 | # Radix-51 arithmetic using u128 57 | radix_51 = [] 58 | 59 | # The development profile, used for `cargo build`. 60 | [profile.dev] 61 | opt-level = 0 # controls the `--opt-level` the compiler builds with 62 | debug = true # controls whether the compiler passes `-g` 63 | rpath = false # controls whether the compiler passes `-C rpath` 64 | lto = false # controls `-C lto` for binaries and staticlibs 65 | debug-assertions = true # controls whether debug assertions are enabled 66 | codegen-units = 1 # controls whether the compiler passes `-C codegen-units` 67 | # `codegen-units` is ignored when `lto = true` 68 | panic = 'unwind' # panic strategy (`-C panic=...`), can also be 'abort' 69 | 70 | # The release profile, used for `cargo build --release`. 71 | [profile.release] 72 | opt-level = 3 73 | debug = false 74 | rpath = false 75 | lto = false 76 | debug-assertions = false 77 | codegen-units = 1 78 | panic = 'unwind' 79 | 80 | # The testing profile, used for `cargo test`. 81 | [profile.test] 82 | opt-level = 0 83 | debug = true 84 | rpath = false 85 | lto = false 86 | debug-assertions = true 87 | codegen-units = 1 88 | panic = 'unwind' 89 | required-features = ['yolocrypto'] 90 | 91 | # The benchmarking profile, used for `cargo bench`. 92 | [profile.bench] 93 | opt-level = 3 94 | debug = false 95 | rpath = false 96 | lto = false 97 | debug-assertions = false 98 | codegen-units = 1 99 | panic = 'unwind' 100 | 101 | # The documentation profile, used for `cargo doc`. 102 | [profile.doc] 103 | opt-level = 0 104 | debug = true 105 | rpath = false 106 | lto = false 107 | debug-assertions = true 108 | codegen-units = 1 109 | panic = 'unwind' 110 | -------------------------------------------------------------------------------- /curve25519-dalek/README.md: -------------------------------------------------------------------------------- 1 | 2 | # curve25519-dalek [![](https://img.shields.io/crates/v/curve25519-dalek.svg)](https://crates.io/curve25519-dalek) [![](https://docs.rs/curve25519-dalek/badge.svg)](https://docs.rs/curve25519-dalek) [![](https://travis-ci.org/isislovecruft/curve25519-dalek.svg?branch=master)](https://travis-ci.org/isislovecruft/curve25519-dalek) 3 | 4 | **A low-level cryptographic library for point, group, field, and scalar 5 | operations on a curve isomorphic to the twisted Edwards curve defined by -x²+y² 6 | = 1 - 121665/121666 x²y² over GF(2²⁵⁵ - 19).** 7 | 8 | **SPOILER ALERT:** *The Twelfth Doctor's first encounter with the Daleks is in 9 | his second full episode, "Into the Dalek". A beleaguered ship of the "Combined 10 | Galactic Resistance" has discovered a broken Dalek that has turned "good", 11 | desiring to kill all other Daleks. The Doctor, Clara and a team of soldiers 12 | are miniaturized and enter the Dalek, which the Doctor names Rusty. They 13 | repair the damage, but accidentally restore it to its original nature, causing 14 | it to go on the rampage and alert the Dalek fleet to the whereabouts of the 15 | rebel ship. However, the Doctor manages to return Rusty to its previous state 16 | by linking his mind with the Dalek's: Rusty shares the Doctor's view of the 17 | universe's beauty, but also his deep hatred of the Daleks. Rusty destroys the 18 | other Daleks and departs the ship, determined to track down and bring an end 19 | to the Dalek race.* 20 | 21 | Significant portions of this code are ported from [Adam Langley's 22 | Golang ed25519 library](https://github.com/agl/ed25519), which is in 23 | turn a port of the reference `ref10` implementation. 24 | 25 | ## Warning 26 | 27 | This code has **not** yet received sufficient peer review by other qualified 28 | cryptographers to be considered in any way, shape, or form, safe. Further, 29 | this library does **not** provide high-level routines such as encryption and 30 | decryption or signing and verification. Instead, it is a low-level library, 31 | intended for other cryptographers who would like to implement their own 32 | primitives using this curve. (For an example of how one would implement a 33 | signature scheme using this library, see 34 | [ed25519-dalek](https://github.com/isislovecruft/ed25519-dalek).) 35 | 36 | **USE AT YOUR OWN RISK** 37 | 38 | ## Documentation 39 | 40 | Extensive documentation is available [here](https://docs.rs/curve25519-dalek). 41 | 42 | # Installation 43 | 44 | To install, add the following to the dependencies section of your project's 45 | `Cargo.toml`: 46 | 47 | curve25519-dalek = "^0.9" 48 | 49 | Then, in your library or executable source, add: 50 | 51 | extern crate curve25519_dalek 52 | 53 | On nightly Rust, using the `nightly` feature enables a radix-51 field 54 | arithmetic implementation using `u128`s, which is approximately twice as 55 | fast. 56 | 57 | ## TODO 58 | 59 | * Implement hashing to a point on the curve (Elligator). 60 | * Make a new `mask` type in `subtle.rs` and return that instead of `u8`s. 61 | * Implement all utilities in Golang's `crypto/subtle` package, and 62 | move the module to its own crate. 63 | -------------------------------------------------------------------------------- /curve25519-dalek/fuzz/.gitignore: -------------------------------------------------------------------------------- 1 | 2 | target 3 | corpus 4 | artifacts 5 | -------------------------------------------------------------------------------- /curve25519-dalek/fuzz/Cargo.toml: -------------------------------------------------------------------------------- 1 | 2 | [package] 3 | name = "curve25519-dalek-fuzz" 4 | version = "0.0.1" 5 | authors = ["Automatically generated"] 6 | publish = false 7 | 8 | [package.metadata] 9 | cargo-fuzz = true 10 | 11 | [dependencies.curve25519-dalek] 12 | path = ".." 13 | features = ["yolocrypto"] 14 | 15 | [dependencies.libfuzzer-sys] 16 | git = "https://github.com/rust-fuzz/libfuzzer-sys.git" 17 | 18 | # Prevent this from interfering with workspaces 19 | [workspace] 20 | members = ["."] 21 | 22 | [[bin]] 23 | name = "decaf" 24 | path = "fuzzers/decaf.rs" 25 | -------------------------------------------------------------------------------- /curve25519-dalek/fuzz/fuzzers/decaf.rs: -------------------------------------------------------------------------------- 1 | #![no_main] 2 | #[macro_use] extern crate libfuzzer_sys; 3 | extern crate curve25519_dalek; 4 | 5 | use curve25519_dalek::curve::ValidityCheck; 6 | use curve25519_dalek::decaf::DecafPoint; 7 | use curve25519_dalek::field::FieldElement; 8 | 9 | fuzz_target!(|data: &[u8]| { 10 | if data.len() != 32 { 11 | return; 12 | } 13 | let mut field_bytes = [0u8; 32]; 14 | for (by, data) in field_bytes.iter_mut().zip(data.iter()) { 15 | *by = *data; 16 | } 17 | let fe = FieldElement::from_bytes(&field_bytes); 18 | let p = DecafPoint::elligator_decaf_flavour(&fe); 19 | assert!(p.0.is_valid()); 20 | p.compress(); 21 | }); 22 | -------------------------------------------------------------------------------- /curve25519-dalek/src/lib.rs: -------------------------------------------------------------------------------- 1 | // -*- mode: rust; coding: utf-8; -*- 2 | // 3 | // To the extent possible under law, the authors have waived all copyright and 4 | // related or neighboring rights to curve25519-dalek, using the Creative 5 | // Commons "CC0" public domain dedication. 6 | // See for full details. 7 | // 8 | // Authors: 9 | // - Isis Agora Lovecruft 10 | // - Henry de Valence 11 | 12 | #![cfg_attr(not(feature = "std"), no_std)] 13 | #![cfg_attr(feature = "alloc", feature(alloc))] 14 | #![cfg_attr(feature = "nightly", feature(i128_type))] 15 | #![cfg_attr(feature = "bench", feature(test))] 16 | #![cfg_attr(all(feature = "nightly", feature = "std"), feature(zero_one))] 17 | 18 | #![allow(unused_features)] 19 | #![deny(missing_docs)] // refuse to compile if documentation is missing 20 | 21 | //! # curve25519-dalek 22 | //! 23 | //! **A Rust implementation of field and group operations on an Edwards curve 24 | //! over GF(2^255 - 19).** 25 | //! 26 | //! **[SPOILER ALERT]** The Twelfth Doctor's first encounter with the Daleks is 27 | //! in his second full episode, "Into the Dalek". A beleaguered ship of the 28 | //! "Combined Galactic Resistance" has discovered a broken Dalek that has 29 | //! turned "good", desiring to kill all other Daleks. The Doctor, Clara and a 30 | //! team of soldiers are miniaturized and enter the Dalek, which the Doctor 31 | //! names Rusty. They repair the damage, but accidentally restore it to its 32 | //! original nature, causing it to go on the rampage and alert the Dalek fleet 33 | //! to the whereabouts of the rebel ship. However, the Doctor manages to 34 | //! return Rusty to its previous state by linking his mind with the Dalek's: 35 | //! Rusty shares the Doctor's view of the universe's beauty, but also his deep 36 | //! hatred of the Daleks. Rusty destroys the other Daleks and departs the 37 | //! ship, determined to track down and bring an end to the Dalek race. 38 | 39 | #[cfg(all(test, feature = "bench"))] 40 | extern crate test; 41 | 42 | #[cfg(test)] 43 | extern crate sha2; 44 | 45 | #[macro_use] 46 | extern crate arrayref; 47 | 48 | extern crate generic_array; 49 | extern crate digest; 50 | extern crate subtle; 51 | 52 | #[cfg(feature = "serde")] 53 | extern crate serde; 54 | #[cfg(all(test, feature = "serde"))] 55 | extern crate serde_cbor; 56 | 57 | #[cfg(feature = "std")] 58 | extern crate core; 59 | 60 | #[cfg(feature = "std")] 61 | extern crate rand; 62 | 63 | #[cfg(feature = "alloc")] 64 | extern crate alloc; 65 | 66 | // Modules for low-level operations directly on field elements and curve points. 67 | 68 | pub mod field; 69 | pub mod scalar; 70 | pub mod curve; 71 | 72 | // Feature gate decaf while our implementation is unfinished and probably incorrect. 73 | #[cfg(feature = "yolocrypto")] 74 | pub mod decaf; 75 | 76 | // Other miscelaneous utilities. 77 | 78 | pub mod utils; 79 | 80 | // Low-level curve and point constants, as well as pre-computed curve group elements. 81 | 82 | pub mod constants; 83 | -------------------------------------------------------------------------------- /curve25519-dalek/src/utils.rs: -------------------------------------------------------------------------------- 1 | // -*- mode: rust; -*- 2 | // 3 | // To the extent possible under law, the authors have waived all copyright and 4 | // related or neighboring rights to curve25519-dalek, using the Creative 5 | // Commons "CC0" public domain dedication. See 6 | // for full details. 7 | // 8 | // Authors: 9 | // - Isis Agora Lovecruft 10 | // - Henry de Valence 11 | 12 | //! Miscellaneous common utility functions. 13 | 14 | /// Convert an array of (at least) three bytes into an i64. 15 | #[inline] 16 | //#[allow(dead_code)] 17 | pub fn load3(input: &[u8]) -> i64 { 18 | (input[0] as i64) 19 | | ((input[1] as i64) << 8) 20 | | ((input[2] as i64) << 16) 21 | } 22 | 23 | /// Convert an array of (at least) four bytes into an i64. 24 | #[inline] 25 | //#[allow(dead_code)] 26 | pub fn load4(input: &[u8]) -> i64 { 27 | (input[0] as i64) 28 | | ((input[1] as i64) << 8) 29 | | ((input[2] as i64) << 16) 30 | | ((input[3] as i64) << 24) 31 | } 32 | 33 | /// Convert an array of (at least) eight bytes into a u64. 34 | #[inline] 35 | //#[allow(dead_code)] 36 | pub fn load8(input: &[u8]) -> u64 { 37 | (input[0] as u64) 38 | | ((input[1] as u64) << 8) 39 | | ((input[2] as u64) << 16) 40 | | ((input[3] as u64) << 24) 41 | | ((input[4] as u64) << 32) 42 | | ((input[5] as u64) << 40) 43 | | ((input[6] as u64) << 48) 44 | | ((input[7] as u64) << 56) 45 | } 46 | -------------------------------------------------------------------------------- /curve25519-go/const_amd64.h: -------------------------------------------------------------------------------- 1 | // Copyright 2012 The Go Authors. All rights reserved. 2 | // Use of this source code is governed by a BSD-style 3 | // license that can be found in the LICENSE file. 4 | 5 | // This code was translated into a form compatible with 6a from the public 6 | // domain sources in SUPERCOP: https://bench.cr.yp.to/supercop.html 7 | 8 | #define REDMASK51 0x0007FFFFFFFFFFFF 9 | -------------------------------------------------------------------------------- /curve25519-go/const_amd64.s: -------------------------------------------------------------------------------- 1 | // Copyright 2012 The Go Authors. All rights reserved. 2 | // Use of this source code is governed by a BSD-style 3 | // license that can be found in the LICENSE file. 4 | 5 | // This code was translated into a form compatible with 6a from the public 6 | // domain sources in SUPERCOP: https://bench.cr.yp.to/supercop.html 7 | 8 | // +build amd64,!gccgo,!appengine 9 | 10 | // These constants cannot be encoded in non-MOVQ immediates. 11 | // We access them directly from memory instead. 12 | 13 | DATA ·_121666_213(SB)/8, $996687872 14 | GLOBL ·_121666_213(SB), 8, $8 15 | 16 | DATA ·_2P0(SB)/8, $0xFFFFFFFFFFFDA 17 | GLOBL ·_2P0(SB), 8, $8 18 | 19 | DATA ·_2P1234(SB)/8, $0xFFFFFFFFFFFFE 20 | GLOBL ·_2P1234(SB), 8, $8 21 | -------------------------------------------------------------------------------- /curve25519-go/cswap_amd64.s: -------------------------------------------------------------------------------- 1 | // Copyright 2012 The Go Authors. All rights reserved. 2 | // Use of this source code is governed by a BSD-style 3 | // license that can be found in the LICENSE file. 4 | 5 | // +build amd64,!gccgo,!appengine 6 | 7 | // func cswap(inout *[4][5]uint64, v uint64) 8 | TEXT ·cswap(SB),7,$0 9 | MOVQ inout+0(FP),DI 10 | MOVQ v+8(FP),SI 11 | 12 | SUBQ $1, SI 13 | NOTQ SI 14 | MOVQ SI, X15 15 | PSHUFD $0x44, X15, X15 16 | 17 | MOVOU 0(DI), X0 18 | MOVOU 16(DI), X2 19 | MOVOU 32(DI), X4 20 | MOVOU 48(DI), X6 21 | MOVOU 64(DI), X8 22 | MOVOU 80(DI), X1 23 | MOVOU 96(DI), X3 24 | MOVOU 112(DI), X5 25 | MOVOU 128(DI), X7 26 | MOVOU 144(DI), X9 27 | 28 | MOVO X1, X10 29 | MOVO X3, X11 30 | MOVO X5, X12 31 | MOVO X7, X13 32 | MOVO X9, X14 33 | 34 | PXOR X0, X10 35 | PXOR X2, X11 36 | PXOR X4, X12 37 | PXOR X6, X13 38 | PXOR X8, X14 39 | PAND X15, X10 40 | PAND X15, X11 41 | PAND X15, X12 42 | PAND X15, X13 43 | PAND X15, X14 44 | PXOR X10, X0 45 | PXOR X10, X1 46 | PXOR X11, X2 47 | PXOR X11, X3 48 | PXOR X12, X4 49 | PXOR X12, X5 50 | PXOR X13, X6 51 | PXOR X13, X7 52 | PXOR X14, X8 53 | PXOR X14, X9 54 | 55 | MOVOU X0, 0(DI) 56 | MOVOU X2, 16(DI) 57 | MOVOU X4, 32(DI) 58 | MOVOU X6, 48(DI) 59 | MOVOU X8, 64(DI) 60 | MOVOU X1, 80(DI) 61 | MOVOU X3, 96(DI) 62 | MOVOU X5, 112(DI) 63 | MOVOU X7, 128(DI) 64 | MOVOU X9, 144(DI) 65 | RET 66 | -------------------------------------------------------------------------------- /curve25519-go/curve25519_test.go: -------------------------------------------------------------------------------- 1 | // Copyright 2012 The Go Authors. All rights reserved. 2 | // Use of this source code is governed by a BSD-style 3 | // license that can be found in the LICENSE file. 4 | 5 | package curve25519 6 | 7 | import ( 8 | "fmt" 9 | "testing" 10 | ) 11 | 12 | const expectedHex = "89161fde887b2b53de549af483940106ecc114d6982daa98256de23bdf77661a" 13 | 14 | func TestBaseScalarMult(t *testing.T) { 15 | var a, b [32]byte 16 | in := &a 17 | out := &b 18 | a[0] = 1 19 | 20 | for i := 0; i < 200; i++ { 21 | ScalarBaseMult(out, in) 22 | in, out = out, in 23 | } 24 | 25 | result := fmt.Sprintf("%x", in[:]) 26 | if result != expectedHex { 27 | t.Errorf("incorrect result: got %s, want %s", result, expectedHex) 28 | } 29 | } 30 | 31 | func BenchmarkScalarBaseMult(b *testing.B) { 32 | var in, out [32]byte 33 | in[0] = 1 34 | 35 | b.SetBytes(32) 36 | for i := 0; i < b.N; i++ { 37 | ScalarBaseMult(&out, &in) 38 | } 39 | } 40 | -------------------------------------------------------------------------------- /curve25519-go/doc.go: -------------------------------------------------------------------------------- 1 | // Copyright 2012 The Go Authors. All rights reserved. 2 | // Use of this source code is governed by a BSD-style 3 | // license that can be found in the LICENSE file. 4 | 5 | // Package curve25519 provides an implementation of scalar multiplication on 6 | // the elliptic curve known as curve25519. See https://cr.yp.to/ecdh.html 7 | package curve25519 // import "golang.org/x/crypto/curve25519" 8 | 9 | // basePoint is the x coordinate of the generator of the curve. 10 | var basePoint = [32]byte{9, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0} 11 | 12 | // ScalarMult sets dst to the product in*base where dst and base are the x 13 | // coordinates of group points and all values are in little-endian form. 14 | func ScalarMult(dst, in, base *[32]byte) { 15 | scalarMult(dst, in, base) 16 | } 17 | 18 | // ScalarBaseMult sets dst to the product in*base where dst and base are the x 19 | // coordinates of group points, base is the standard generator and all values 20 | // are in little-endian form. 21 | func ScalarBaseMult(dst, in *[32]byte) { 22 | ScalarMult(dst, in, &basePoint) 23 | } 24 | -------------------------------------------------------------------------------- /curve25519-go/freeze_amd64.s: -------------------------------------------------------------------------------- 1 | // Copyright 2012 The Go Authors. All rights reserved. 2 | // Use of this source code is governed by a BSD-style 3 | // license that can be found in the LICENSE file. 4 | 5 | // This code was translated into a form compatible with 6a from the public 6 | // domain sources in SUPERCOP: https://bench.cr.yp.to/supercop.html 7 | 8 | // +build amd64,!gccgo,!appengine 9 | 10 | #include "const_amd64.h" 11 | 12 | // func freeze(inout *[5]uint64) 13 | TEXT ·freeze(SB),7,$0-8 14 | MOVQ inout+0(FP), DI 15 | 16 | MOVQ 0(DI),SI 17 | MOVQ 8(DI),DX 18 | MOVQ 16(DI),CX 19 | MOVQ 24(DI),R8 20 | MOVQ 32(DI),R9 21 | MOVQ $REDMASK51,AX 22 | MOVQ AX,R10 23 | SUBQ $18,R10 24 | MOVQ $3,R11 25 | REDUCELOOP: 26 | MOVQ SI,R12 27 | SHRQ $51,R12 28 | ANDQ AX,SI 29 | ADDQ R12,DX 30 | MOVQ DX,R12 31 | SHRQ $51,R12 32 | ANDQ AX,DX 33 | ADDQ R12,CX 34 | MOVQ CX,R12 35 | SHRQ $51,R12 36 | ANDQ AX,CX 37 | ADDQ R12,R8 38 | MOVQ R8,R12 39 | SHRQ $51,R12 40 | ANDQ AX,R8 41 | ADDQ R12,R9 42 | MOVQ R9,R12 43 | SHRQ $51,R12 44 | ANDQ AX,R9 45 | IMUL3Q $19,R12,R12 46 | ADDQ R12,SI 47 | SUBQ $1,R11 48 | JA REDUCELOOP 49 | MOVQ $1,R12 50 | CMPQ R10,SI 51 | CMOVQLT R11,R12 52 | CMPQ AX,DX 53 | CMOVQNE R11,R12 54 | CMPQ AX,CX 55 | CMOVQNE R11,R12 56 | CMPQ AX,R8 57 | CMOVQNE R11,R12 58 | CMPQ AX,R9 59 | CMOVQNE R11,R12 60 | NEGQ R12 61 | ANDQ R12,AX 62 | ANDQ R12,R10 63 | SUBQ R10,SI 64 | SUBQ AX,DX 65 | SUBQ AX,CX 66 | SUBQ AX,R8 67 | SUBQ AX,R9 68 | MOVQ SI,0(DI) 69 | MOVQ DX,8(DI) 70 | MOVQ CX,16(DI) 71 | MOVQ R8,24(DI) 72 | MOVQ R9,32(DI) 73 | RET 74 | -------------------------------------------------------------------------------- /curve25519-go/mul_amd64.s: -------------------------------------------------------------------------------- 1 | // Copyright 2012 The Go Authors. All rights reserved. 2 | // Use of this source code is governed by a BSD-style 3 | // license that can be found in the LICENSE file. 4 | 5 | // This code was translated into a form compatible with 6a from the public 6 | // domain sources in SUPERCOP: https://bench.cr.yp.to/supercop.html 7 | 8 | // +build amd64,!gccgo,!appengine 9 | 10 | #include "const_amd64.h" 11 | 12 | // func mul(dest, a, b *[5]uint64) 13 | TEXT ·mul(SB),0,$16-24 14 | MOVQ dest+0(FP), DI 15 | MOVQ a+8(FP), SI 16 | MOVQ b+16(FP), DX 17 | 18 | MOVQ DX,CX 19 | MOVQ 24(SI),DX 20 | IMUL3Q $19,DX,AX 21 | MOVQ AX,0(SP) 22 | MULQ 16(CX) 23 | MOVQ AX,R8 24 | MOVQ DX,R9 25 | MOVQ 32(SI),DX 26 | IMUL3Q $19,DX,AX 27 | MOVQ AX,8(SP) 28 | MULQ 8(CX) 29 | ADDQ AX,R8 30 | ADCQ DX,R9 31 | MOVQ 0(SI),AX 32 | MULQ 0(CX) 33 | ADDQ AX,R8 34 | ADCQ DX,R9 35 | MOVQ 0(SI),AX 36 | MULQ 8(CX) 37 | MOVQ AX,R10 38 | MOVQ DX,R11 39 | MOVQ 0(SI),AX 40 | MULQ 16(CX) 41 | MOVQ AX,R12 42 | MOVQ DX,R13 43 | MOVQ 0(SI),AX 44 | MULQ 24(CX) 45 | MOVQ AX,R14 46 | MOVQ DX,R15 47 | MOVQ 0(SI),AX 48 | MULQ 32(CX) 49 | MOVQ AX,BX 50 | MOVQ DX,BP 51 | MOVQ 8(SI),AX 52 | MULQ 0(CX) 53 | ADDQ AX,R10 54 | ADCQ DX,R11 55 | MOVQ 8(SI),AX 56 | MULQ 8(CX) 57 | ADDQ AX,R12 58 | ADCQ DX,R13 59 | MOVQ 8(SI),AX 60 | MULQ 16(CX) 61 | ADDQ AX,R14 62 | ADCQ DX,R15 63 | MOVQ 8(SI),AX 64 | MULQ 24(CX) 65 | ADDQ AX,BX 66 | ADCQ DX,BP 67 | MOVQ 8(SI),DX 68 | IMUL3Q $19,DX,AX 69 | MULQ 32(CX) 70 | ADDQ AX,R8 71 | ADCQ DX,R9 72 | MOVQ 16(SI),AX 73 | MULQ 0(CX) 74 | ADDQ AX,R12 75 | ADCQ DX,R13 76 | MOVQ 16(SI),AX 77 | MULQ 8(CX) 78 | ADDQ AX,R14 79 | ADCQ DX,R15 80 | MOVQ 16(SI),AX 81 | MULQ 16(CX) 82 | ADDQ AX,BX 83 | ADCQ DX,BP 84 | MOVQ 16(SI),DX 85 | IMUL3Q $19,DX,AX 86 | MULQ 24(CX) 87 | ADDQ AX,R8 88 | ADCQ DX,R9 89 | MOVQ 16(SI),DX 90 | IMUL3Q $19,DX,AX 91 | MULQ 32(CX) 92 | ADDQ AX,R10 93 | ADCQ DX,R11 94 | MOVQ 24(SI),AX 95 | MULQ 0(CX) 96 | ADDQ AX,R14 97 | ADCQ DX,R15 98 | MOVQ 24(SI),AX 99 | MULQ 8(CX) 100 | ADDQ AX,BX 101 | ADCQ DX,BP 102 | MOVQ 0(SP),AX 103 | MULQ 24(CX) 104 | ADDQ AX,R10 105 | ADCQ DX,R11 106 | MOVQ 0(SP),AX 107 | MULQ 32(CX) 108 | ADDQ AX,R12 109 | ADCQ DX,R13 110 | MOVQ 32(SI),AX 111 | MULQ 0(CX) 112 | ADDQ AX,BX 113 | ADCQ DX,BP 114 | MOVQ 8(SP),AX 115 | MULQ 16(CX) 116 | ADDQ AX,R10 117 | ADCQ DX,R11 118 | MOVQ 8(SP),AX 119 | MULQ 24(CX) 120 | ADDQ AX,R12 121 | ADCQ DX,R13 122 | MOVQ 8(SP),AX 123 | MULQ 32(CX) 124 | ADDQ AX,R14 125 | ADCQ DX,R15 126 | MOVQ $REDMASK51,SI 127 | SHLQ $13,R9:R8 128 | ANDQ SI,R8 129 | SHLQ $13,R11:R10 130 | ANDQ SI,R10 131 | ADDQ R9,R10 132 | SHLQ $13,R13:R12 133 | ANDQ SI,R12 134 | ADDQ R11,R12 135 | SHLQ $13,R15:R14 136 | ANDQ SI,R14 137 | ADDQ R13,R14 138 | SHLQ $13,BP:BX 139 | ANDQ SI,BX 140 | ADDQ R15,BX 141 | IMUL3Q $19,BP,DX 142 | ADDQ DX,R8 143 | MOVQ R8,DX 144 | SHRQ $51,DX 145 | ADDQ R10,DX 146 | MOVQ DX,CX 147 | SHRQ $51,DX 148 | ANDQ SI,R8 149 | ADDQ R12,DX 150 | MOVQ DX,R9 151 | SHRQ $51,DX 152 | ANDQ SI,CX 153 | ADDQ R14,DX 154 | MOVQ DX,AX 155 | SHRQ $51,DX 156 | ANDQ SI,R9 157 | ADDQ BX,DX 158 | MOVQ DX,R10 159 | SHRQ $51,DX 160 | ANDQ SI,AX 161 | IMUL3Q $19,DX,DX 162 | ADDQ DX,R8 163 | ANDQ SI,R10 164 | MOVQ R8,0(DI) 165 | MOVQ CX,8(DI) 166 | MOVQ R9,16(DI) 167 | MOVQ AX,24(DI) 168 | MOVQ R10,32(DI) 169 | RET 170 | -------------------------------------------------------------------------------- /curve25519-go/square_amd64.s: -------------------------------------------------------------------------------- 1 | // Copyright 2012 The Go Authors. All rights reserved. 2 | // Use of this source code is governed by a BSD-style 3 | // license that can be found in the LICENSE file. 4 | 5 | // This code was translated into a form compatible with 6a from the public 6 | // domain sources in SUPERCOP: https://bench.cr.yp.to/supercop.html 7 | 8 | // +build amd64,!gccgo,!appengine 9 | 10 | #include "const_amd64.h" 11 | 12 | // func square(out, in *[5]uint64) 13 | TEXT ·square(SB),7,$0-16 14 | MOVQ out+0(FP), DI 15 | MOVQ in+8(FP), SI 16 | 17 | MOVQ 0(SI),AX 18 | MULQ 0(SI) 19 | MOVQ AX,CX 20 | MOVQ DX,R8 21 | MOVQ 0(SI),AX 22 | SHLQ $1,AX 23 | MULQ 8(SI) 24 | MOVQ AX,R9 25 | MOVQ DX,R10 26 | MOVQ 0(SI),AX 27 | SHLQ $1,AX 28 | MULQ 16(SI) 29 | MOVQ AX,R11 30 | MOVQ DX,R12 31 | MOVQ 0(SI),AX 32 | SHLQ $1,AX 33 | MULQ 24(SI) 34 | MOVQ AX,R13 35 | MOVQ DX,R14 36 | MOVQ 0(SI),AX 37 | SHLQ $1,AX 38 | MULQ 32(SI) 39 | MOVQ AX,R15 40 | MOVQ DX,BX 41 | MOVQ 8(SI),AX 42 | MULQ 8(SI) 43 | ADDQ AX,R11 44 | ADCQ DX,R12 45 | MOVQ 8(SI),AX 46 | SHLQ $1,AX 47 | MULQ 16(SI) 48 | ADDQ AX,R13 49 | ADCQ DX,R14 50 | MOVQ 8(SI),AX 51 | SHLQ $1,AX 52 | MULQ 24(SI) 53 | ADDQ AX,R15 54 | ADCQ DX,BX 55 | MOVQ 8(SI),DX 56 | IMUL3Q $38,DX,AX 57 | MULQ 32(SI) 58 | ADDQ AX,CX 59 | ADCQ DX,R8 60 | MOVQ 16(SI),AX 61 | MULQ 16(SI) 62 | ADDQ AX,R15 63 | ADCQ DX,BX 64 | MOVQ 16(SI),DX 65 | IMUL3Q $38,DX,AX 66 | MULQ 24(SI) 67 | ADDQ AX,CX 68 | ADCQ DX,R8 69 | MOVQ 16(SI),DX 70 | IMUL3Q $38,DX,AX 71 | MULQ 32(SI) 72 | ADDQ AX,R9 73 | ADCQ DX,R10 74 | MOVQ 24(SI),DX 75 | IMUL3Q $19,DX,AX 76 | MULQ 24(SI) 77 | ADDQ AX,R9 78 | ADCQ DX,R10 79 | MOVQ 24(SI),DX 80 | IMUL3Q $38,DX,AX 81 | MULQ 32(SI) 82 | ADDQ AX,R11 83 | ADCQ DX,R12 84 | MOVQ 32(SI),DX 85 | IMUL3Q $19,DX,AX 86 | MULQ 32(SI) 87 | ADDQ AX,R13 88 | ADCQ DX,R14 89 | MOVQ $REDMASK51,SI 90 | SHLQ $13,R8:CX 91 | ANDQ SI,CX 92 | SHLQ $13,R10:R9 93 | ANDQ SI,R9 94 | ADDQ R8,R9 95 | SHLQ $13,R12:R11 96 | ANDQ SI,R11 97 | ADDQ R10,R11 98 | SHLQ $13,R14:R13 99 | ANDQ SI,R13 100 | ADDQ R12,R13 101 | SHLQ $13,BX:R15 102 | ANDQ SI,R15 103 | ADDQ R14,R15 104 | IMUL3Q $19,BX,DX 105 | ADDQ DX,CX 106 | MOVQ CX,DX 107 | SHRQ $51,DX 108 | ADDQ R9,DX 109 | ANDQ SI,CX 110 | MOVQ DX,R8 111 | SHRQ $51,DX 112 | ADDQ R11,DX 113 | ANDQ SI,R8 114 | MOVQ DX,R9 115 | SHRQ $51,DX 116 | ADDQ R13,DX 117 | ANDQ SI,R9 118 | MOVQ DX,AX 119 | SHRQ $51,DX 120 | ADDQ R15,DX 121 | ANDQ SI,AX 122 | MOVQ DX,R10 123 | SHRQ $51,DX 124 | IMUL3Q $19,DX,DX 125 | ADDQ DX,CX 126 | ANDQ SI,R10 127 | MOVQ CX,0(DI) 128 | MOVQ R8,8(DI) 129 | MOVQ R9,16(DI) 130 | MOVQ AX,24(DI) 131 | MOVQ R10,32(DI) 132 | RET 133 | -------------------------------------------------------------------------------- /ed25519-dalek/.gitignore: -------------------------------------------------------------------------------- 1 | target 2 | Cargo.lock 3 | 4 | .cargo 5 | 6 | *~ 7 | \#* 8 | .\#* 9 | *.swp 10 | *.orig 11 | *.bak 12 | 13 | *.s 14 | -------------------------------------------------------------------------------- /ed25519-dalek/.travis.yml: -------------------------------------------------------------------------------- 1 | language: rust 2 | 3 | rust: 4 | - stable 5 | - beta 6 | - nightly 7 | 8 | env: 9 | - TEST_COMMAND=test FEATURES='' 10 | 11 | matrix: 12 | include: 13 | - rust: nightly 14 | env: TEST_COMMAND=build FEATURES=--no-default-features 15 | - rust: nightly 16 | env: TEST_COMMAND=test FEATURES=--features="nightly" 17 | - rust: nightly 18 | env: TEST_COMMAND=bench FEATURES=--features="bench" 19 | - rust: nightly 20 | env: TEST_COMMAND=bench FEATURES=--features="nightly bench" 21 | 22 | script: 23 | - cargo $TEST_COMMAND $FEATURES 24 | -------------------------------------------------------------------------------- /ed25519-dalek/Cargo.toml: -------------------------------------------------------------------------------- 1 | [package] 2 | name = "ed25519-dalek" 3 | version = "0.3.2" 4 | authors = ["Isis Lovecruft "] 5 | readme = "README.md" 6 | license = "CC0-1.0" 7 | repository = "https://github.com/isislovecruft/ed25519-dalek" 8 | homepage = "https://code.ciph.re/isis/ed25519-dalek" 9 | documentation = "https://docs.rs/ed25519-dalek" 10 | keywords = ["cryptography", "ed25519", "curve25519", "signature", "ECC"] 11 | categories = ["cryptography", "no-std"] 12 | description = "Fast and efficient ed25519 signing and verification in pure Rust." 13 | exclude = [ ".gitignore", "TESTVECTORS", "res/*" ] 14 | 15 | [badges] 16 | travis-ci = { repository = "isislovecruft/ed25519-dalek", branch = "master"} 17 | 18 | [dependencies] 19 | arrayref = "0.3.3" 20 | 21 | [dependencies.curve25519-dalek] 22 | version = "^0.7" 23 | default-features = false 24 | 25 | [dependencies.rand] 26 | optional = true 27 | version = "^0.3" 28 | 29 | [dependencies.digest] 30 | version = "^0.5" 31 | 32 | [dependencies.generic-array] 33 | # same version that digest depends on 34 | version = "^0.6" 35 | 36 | [dev-dependencies] 37 | rustc-serialize = "0.3" 38 | sha2 = "^0.5" 39 | 40 | [features] 41 | default = ["std"] 42 | std = ["rand", "curve25519-dalek/std"] 43 | bench = [] 44 | nightly = ["curve25519-dalek/nightly"] 45 | -------------------------------------------------------------------------------- /ed25519-dalek/res/ed25519-malleability.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/gtank/defcon25_crypto_village/4c0bc99e9cb667644ea5a3b3085ae3a371cbc355/ed25519-dalek/res/ed25519-malleability.png -------------------------------------------------------------------------------- /ed25519-go/testdata/sign.input.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/gtank/defcon25_crypto_village/4c0bc99e9cb667644ea5a3b3085ae3a371cbc355/ed25519-go/testdata/sign.input.gz -------------------------------------------------------------------------------- /ed25519-gtank/LICENSE: -------------------------------------------------------------------------------- 1 | Copyright 2017 George Tankersley. All rights reserved. 2 | 3 | Redistribution and use in source and binary forms, with or without 4 | modification, are permitted provided that the following conditions are met: 5 | 6 | 1. Redistributions of source code must retain the above copyright notice, this 7 | list of conditions and the following disclaimer. 8 | 9 | 2. Redistributions in binary form must reproduce the above copyright notice, 10 | this list of conditions and the following disclaimer in the documentation 11 | and/or other materials provided with the distribution. 12 | 13 | 3. Neither the name of the copyright holder nor the names of its contributors 14 | may be used to endorse or promote products derived from this software without 15 | specific prior written permission. 16 | 17 | THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND 18 | ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED 19 | WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE 20 | DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE 21 | FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 22 | DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR 23 | SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER 24 | CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, 25 | OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 26 | OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27 | -------------------------------------------------------------------------------- /ed25519-gtank/README: -------------------------------------------------------------------------------- 1 | This is foremost an implementation of the curve Ed25519 that satisfies Go's 2 | elliptic.Curve interface. It targets amd64 systems, and is eventually intended 3 | to be a legible general-purpose library along the lines of curve25519-dalek. 4 | 5 | It is also an implementation of GF(2^255-19) field operations in a 64-bit 6 | representation, in both pure Go and plan9 assembly for amd64. This code is 7 | currently package-internal. 8 | 9 | The library is a WORK IN PROGRESS. Everything will change dramatically as 10 | development continues. There are no guarantees of stability, functionality, 11 | correctness, or safety. We aren't open yet, come back later! 12 | -------------------------------------------------------------------------------- /ed25519-gtank/doc.go: -------------------------------------------------------------------------------- 1 | // Package ed25519 implements an elliptic.Curve interface on top of the twisted 2 | // Edwards curve -x^2 + y^2 = 1 + -(121665/121666)*x^2*y^2. This is better 3 | // known as the Edwards curve equivalent to curve25519, and is the curve used 4 | // by the Ed25519 signature scheme. 5 | // 6 | // Because of the Curve interface, this package takes input in affine (x,y) 7 | // pairs instead of the more standard compressed Edwards y. 8 | package ed25519 9 | -------------------------------------------------------------------------------- /ed25519-gtank/internal/group/const.go: -------------------------------------------------------------------------------- 1 | package group 2 | 3 | import "github.com/gtank/ed25519/internal/radix51" 4 | 5 | var ( 6 | // d, a constant in the curve equation 7 | D radix51.FieldElement = [5]uint64{929955233495203, 466365720129213, 1662059464998953, 2033849074728123, 1442794654840575} 8 | 9 | // 2*d, used in addition formula 10 | D2 radix51.FieldElement = [5]uint64{1859910466990425, 932731440258426, 1072319116312658, 1815898335770999, 633789495995903} 11 | ) 12 | -------------------------------------------------------------------------------- /ed25519-gtank/internal/radix51/const.go: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2017 George Tankersley. All rights reserved. 2 | // Use of this source code is governed by a BSD-style 3 | // license that can be found in the LICENSE file. 4 | 5 | // Constants used in the implementation of GF(2^255-19) field arithmetic. 6 | package radix51 7 | 8 | const ( 9 | // The vaule 2^51-1, used in carry propagation 10 | maskLow51Bits = uint64(1)<<51 - 1 11 | ) 12 | 13 | var ( 14 | FieldZero FieldElement = [5]uint64{0, 0, 0, 0, 0} 15 | FieldOne FieldElement = [5]uint64{1, 0, 0, 0, 0} 16 | FieldTwo FieldElement = [5]uint64{2, 0, 0, 0, 0} 17 | ) 18 | -------------------------------------------------------------------------------- /ed25519-gtank/internal/radix51/fe_mul_amd64.go: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2017 George Tankersley. All rights reserved. 2 | // Use of this source code is governed by a BSD-style 3 | // license that can be found in the LICENSE file. 4 | 5 | // +build amd64,!noasm 6 | 7 | package radix51 8 | 9 | // go:noescape 10 | func FeMul(out, a, b *FieldElement) 11 | -------------------------------------------------------------------------------- /ed25519-gtank/internal/radix51/fe_square.go: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2017 George Tankersley. All rights reserved. 2 | // Use of this source code is governed by a BSD-style 3 | // license that can be found in the LICENSE file. 4 | 5 | // +build !amd64 noasm 6 | 7 | package radix51 8 | 9 | // FeSquare sets out = x*x 10 | func FeSquare(out, x *FieldElement) { 11 | // Squaring needs only 15 mul instructions. Some inputs are multiplied by 2; 12 | // this is combined with multiplication by 19 where possible. The coefficient 13 | // reduction after squaring is the same as for multiplication. 14 | 15 | var x0, x1, x2, x3, x4 uint64 16 | 17 | x0 = x[0] 18 | x1 = x[1] 19 | x2 = x[2] 20 | x3 = x[3] 21 | x4 = x[4] 22 | 23 | x0_2 := x0 << 1 24 | x1_2 := x1 << 1 25 | 26 | x1_38 := x1 * 38 27 | x2_38 := x2 * 38 28 | x3_38 := x3 * 38 29 | 30 | x3_19 := x3 * 19 31 | x4_19 := x4 * 19 32 | 33 | // r0 = x0*x0 + x1*38*x4 + x2*38*x3 34 | r00, r01 := mul64x64(0, 0, x0, x0) 35 | r00, r01 = mul64x64(r00, r01, x1_38, x4) 36 | r00, r01 = mul64x64(r00, r01, x2_38, x3) 37 | 38 | // r1 = x0*2*x1 + x2*38*x4 + x3*19*x3 39 | r10, r11 := mul64x64(0, 0, x0_2, x1) 40 | r10, r11 = mul64x64(r10, r11, x2_38, x4) 41 | r10, r11 = mul64x64(r10, r11, x3_19, x3) 42 | 43 | // r2 = x0*2*x2 + x1*x1 + x3*38*x4 44 | r20, r21 := mul64x64(0, 0, x0_2, x2) 45 | r20, r21 = mul64x64(r20, r21, x1, x1) 46 | r20, r21 = mul64x64(r20, r21, x3_38, x4) 47 | 48 | // r3 = x0*2*x3 + x1*2*x2 + x4*19*x4 49 | r30, r31 := mul64x64(0, 0, x0_2, x3) 50 | r30, r31 = mul64x64(r30, r31, x1_2, x2) 51 | r30, r31 = mul64x64(r30, r31, x4_19, x4) 52 | 53 | // r4 = x0*2*x4 + x1*2*x3 + x2*x2 54 | r40, r41 := mul64x64(0, 0, x0_2, x4) 55 | r40, r41 = mul64x64(r40, r41, x1_2, x3) 56 | r40, r41 = mul64x64(r40, r41, x2, x2) 57 | 58 | // Same reduction 59 | 60 | r01 = (r01 << 13) | (r00 >> 51) 61 | r00 &= maskLow51Bits 62 | 63 | r11 = (r11 << 13) | (r10 >> 51) 64 | r10 &= maskLow51Bits 65 | r10 += r01 66 | 67 | r21 = (r21 << 13) | (r20 >> 51) 68 | r20 &= maskLow51Bits 69 | r20 += r11 70 | 71 | r31 = (r31 << 13) | (r30 >> 51) 72 | r30 &= maskLow51Bits 73 | r30 += r21 74 | 75 | r41 = (r41 << 13) | (r40 >> 51) 76 | r40 &= maskLow51Bits 77 | r40 += r31 78 | 79 | r41 *= 19 80 | r00 += r41 81 | 82 | r10 += r00 >> 51 83 | r00 &= maskLow51Bits 84 | r20 += r10 >> 51 85 | r10 &= maskLow51Bits 86 | r30 += r20 >> 51 87 | r20 &= maskLow51Bits 88 | r40 += r30 >> 51 89 | r30 &= maskLow51Bits 90 | r00 += (r40 >> 51) * 19 91 | r40 &= maskLow51Bits 92 | 93 | out[0] = r00 94 | out[1] = r10 95 | out[2] = r20 96 | out[3] = r30 97 | out[4] = r40 98 | } 99 | -------------------------------------------------------------------------------- /ed25519-gtank/internal/radix51/fe_square_amd64.go: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2017 George Tankersley. All rights reserved. 2 | // Use of this source code is governed by a BSD-style 3 | // license that can be found in the LICENSE file. 4 | 5 | // +build amd64,!noasm 6 | 7 | package radix51 8 | 9 | // go:noescape 10 | func FeSquare(out, x *FieldElement) 11 | -------------------------------------------------------------------------------- /ed25519-gtank/internal/radix51/mul.go: -------------------------------------------------------------------------------- 1 | // Copyright (c) 2017 George Tankersley. All rights reserved. 2 | // Use of this source code is governed by a BSD-style 3 | // license that can be found in the LICENSE file. 4 | 5 | package radix51 6 | 7 | import "unsafe" 8 | 9 | // mul64x64 multiples two 64-bit numbers and adds them to two accumulators. 10 | // This function is written to ensure it inlines. I am so sorry. 11 | func mul64x64(lo, hi, a, b uint64) (ol uint64, oh uint64) { 12 | t1 := (a>>32)*(b&0xFFFFFFFF) + ((a & 0xFFFFFFFF) * (b & 0xFFFFFFFF) >> 32) 13 | t2 := (a&0xFFFFFFFF)*(b>>32) + (t1 & 0xFFFFFFFF) 14 | ol = (a * b) + lo 15 | cmp := ol < lo 16 | oh = hi + (a>>32)*(b>>32) + t1>>32 + t2>>32 + uint64(*(*byte)(unsafe.Pointer(&cmp))) 17 | return 18 | } 19 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-51-30k/api.h: -------------------------------------------------------------------------------- 1 | #define CRYPTO_SECRETKEYBYTES 64 2 | #define CRYPTO_PUBLICKEYBYTES 32 3 | #define CRYPTO_BYTES 64 4 | #define CRYPTO_DETERMINISTIC 1 5 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-51-30k/architectures: -------------------------------------------------------------------------------- 1 | amd64 2 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-51-30k/batch.c: -------------------------------------------------------------------------------- 1 | #include "crypto_sign.h" 2 | 3 | #include "crypto_verify_32.h" 4 | #include "crypto_hash_sha512.h" 5 | #include "randombytes.h" 6 | 7 | #include "ge25519.h" 8 | #include "hram.h" 9 | 10 | #define MAXBATCH 64 11 | 12 | int crypto_sign_open_batch( 13 | unsigned char* const m[],unsigned long long mlen[], 14 | unsigned char* const sm[],const unsigned long long smlen[], 15 | unsigned char* const pk[], 16 | unsigned long long num 17 | ) 18 | { 19 | int ret = 0; 20 | unsigned long long i, j; 21 | shortsc25519 r[MAXBATCH]; 22 | sc25519 scalars[2*MAXBATCH+1]; 23 | ge25519 points[2*MAXBATCH+1]; 24 | unsigned char hram[crypto_hash_sha512_BYTES]; 25 | unsigned long long batchsize; 26 | 27 | for (i = 0;i < num;++i) mlen[i] = -1; 28 | 29 | while (num >= 3) { 30 | batchsize = num; 31 | if (batchsize > MAXBATCH) batchsize = MAXBATCH; 32 | 33 | for (i = 0;i < batchsize;++i) 34 | if (smlen[i] < 64) goto fallback; 35 | 36 | randombytes((unsigned char*)r,sizeof(shortsc25519) * batchsize); 37 | 38 | /* Computing scalars[0] = ((r1s1 + r2s2 + ...)) */ 39 | for(i=0;iv[0] = x->v[0] + y->v[0]; 6 | r->v[1] = x->v[1] + y->v[1]; 7 | r->v[2] = x->v[2] + y->v[2]; 8 | r->v[3] = x->v[3] + y->v[3]; 9 | r->v[4] = x->v[4] + y->v[4]; 10 | } 11 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-51-30k/fe25519_getparity.c: -------------------------------------------------------------------------------- 1 | #include "fe25519.h" 2 | 3 | unsigned char fe25519_getparity(const fe25519 *x) 4 | { 5 | fe25519 t = *x; 6 | fe25519_freeze(&t); 7 | return (unsigned char)t.v[0] & 1; 8 | } 9 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-51-30k/fe25519_invert.c: -------------------------------------------------------------------------------- 1 | #include "fe25519.h" 2 | 3 | void fe25519_invert(fe25519 *r, const fe25519 *x) 4 | { 5 | fe25519 z2; 6 | fe25519 z9; 7 | fe25519 z11; 8 | fe25519 z2_5_0; 9 | fe25519 z2_10_0; 10 | fe25519 z2_20_0; 11 | fe25519 z2_50_0; 12 | fe25519 z2_100_0; 13 | fe25519 t; 14 | 15 | /* 2 */ fe25519_square(&z2,x); 16 | /* 4 */ fe25519_square(&t,&z2); 17 | /* 8 */ fe25519_square(&t,&t); 18 | /* 9 */ fe25519_mul(&z9,&t,x); 19 | /* 11 */ fe25519_mul(&z11,&z9,&z2); 20 | /* 22 */ fe25519_square(&t,&z11); 21 | /* 2^5 - 2^0 = 31 */ fe25519_mul(&z2_5_0,&t,&z9); 22 | 23 | /* 2^6 - 2^1 */ fe25519_square(&t,&z2_5_0); 24 | /* 2^10 - 2^5 */ fe25519_nsquare(&t,4); 25 | /* 2^10 - 2^0 */ fe25519_mul(&z2_10_0,&t,&z2_5_0); 26 | 27 | /* 2^11 - 2^1 */ fe25519_square(&t,&z2_10_0); 28 | /* 2^20 - 2^10 */ fe25519_nsquare(&t,9); 29 | /* 2^20 - 2^0 */ fe25519_mul(&z2_20_0,&t,&z2_10_0); 30 | 31 | /* 2^21 - 2^1 */ fe25519_square(&t,&z2_20_0); 32 | /* 2^40 - 2^20 */ fe25519_nsquare(&t,19); 33 | /* 2^40 - 2^0 */ fe25519_mul(&t,&t,&z2_20_0); 34 | 35 | /* 2^41 - 2^1 */ fe25519_square(&t,&t); 36 | /* 2^50 - 2^10 */ fe25519_nsquare(&t,9); 37 | /* 2^50 - 2^0 */ fe25519_mul(&z2_50_0,&t,&z2_10_0); 38 | 39 | /* 2^51 - 2^1 */ fe25519_square(&t,&z2_50_0); 40 | /* 2^100 - 2^50 */ fe25519_nsquare(&t,49); 41 | /* 2^100 - 2^0 */ fe25519_mul(&z2_100_0,&t,&z2_50_0); 42 | 43 | /* 2^101 - 2^1 */ fe25519_square(&t,&z2_100_0); 44 | /* 2^200 - 2^100 */ fe25519_nsquare(&t,99); 45 | /* 2^200 - 2^0 */ fe25519_mul(&t,&t,&z2_100_0); 46 | 47 | /* 2^201 - 2^1 */ fe25519_square(&t,&t); 48 | /* 2^250 - 2^50 */ fe25519_nsquare(&t,49); 49 | /* 2^250 - 2^0 */ fe25519_mul(&t,&t,&z2_50_0); 50 | 51 | /* 2^251 - 2^1 */ fe25519_square(&t,&t); 52 | /* 2^252 - 2^2 */ fe25519_square(&t,&t); 53 | /* 2^253 - 2^3 */ fe25519_square(&t,&t); 54 | 55 | /* 2^254 - 2^4 */ fe25519_square(&t,&t); 56 | 57 | /* 2^255 - 2^5 */ fe25519_square(&t,&t); 58 | /* 2^255 - 21 */ fe25519_mul(r,&t,&z11); 59 | } 60 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-51-30k/fe25519_iseq.c: -------------------------------------------------------------------------------- 1 | #include "fe25519.h" 2 | 3 | int fe25519_iseq_vartime(const fe25519 *x, const fe25519 *y) 4 | { 5 | fe25519 t1 = *x; 6 | fe25519 t2 = *y; 7 | fe25519_freeze(&t1); 8 | fe25519_freeze(&t2); 9 | if(t1.v[0] != t2.v[0]) return 0; 10 | if(t1.v[1] != t2.v[1]) return 0; 11 | if(t1.v[2] != t2.v[2]) return 0; 12 | if(t1.v[3] != t2.v[3]) return 0; 13 | if(t1.v[4] != t2.v[4]) return 0; 14 | return 1; 15 | } 16 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-51-30k/fe25519_iszero.c: -------------------------------------------------------------------------------- 1 | #include "fe25519.h" 2 | 3 | int fe25519_iszero_vartime(const fe25519 *x) 4 | { 5 | fe25519 t = *x; 6 | fe25519_freeze(&t); 7 | if (t.v[0]) return 0; 8 | if (t.v[1]) return 0; 9 | if (t.v[2]) return 0; 10 | if (t.v[3]) return 0; 11 | if (t.v[4]) return 0; 12 | return 1; 13 | } 14 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-51-30k/fe25519_neg.c: -------------------------------------------------------------------------------- 1 | #include "fe25519.h" 2 | 3 | void fe25519_neg(fe25519 *r, const fe25519 *x) 4 | { 5 | fe25519 t; 6 | fe25519_setint(&t,0); 7 | fe25519_sub(r,&t,x); 8 | } 9 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-51-30k/fe25519_pack.c: -------------------------------------------------------------------------------- 1 | #include "fe25519.h" 2 | 3 | /* Assumes input x being reduced below 2^255 */ 4 | void fe25519_pack(unsigned char r[32], const fe25519 *x) 5 | { 6 | fe25519 t; 7 | t = *x; 8 | fe25519_freeze(&t); 9 | r[0] = (unsigned char) ( t.v[0] & 0xff); 10 | r[1] = (unsigned char) ((t.v[0] >> 8) & 0xff); 11 | r[2] = (unsigned char) ((t.v[0] >> 16) & 0xff); 12 | r[3] = (unsigned char) ((t.v[0] >> 24) & 0xff); 13 | r[4] = (unsigned char) ((t.v[0] >> 32) & 0xff); 14 | r[5] = (unsigned char) ((t.v[0] >> 40) & 0xff); 15 | r[6] = (unsigned char) ((t.v[0] >> 48)); 16 | 17 | r[6] ^= (unsigned char) ((t.v[1] << 3) & 0xf8); 18 | r[7] = (unsigned char) ((t.v[1] >> 5) & 0xff); 19 | r[8] = (unsigned char) ((t.v[1] >> 13) & 0xff); 20 | r[9] = (unsigned char) ((t.v[1] >> 21) & 0xff); 21 | r[10] = (unsigned char) ((t.v[1] >> 29) & 0xff); 22 | r[11] = (unsigned char) ((t.v[1] >> 37) & 0xff); 23 | r[12] = (unsigned char) ((t.v[1] >> 45)); 24 | 25 | r[12] ^= (unsigned char) ((t.v[2] << 6) & 0xc0); 26 | r[13] = (unsigned char) ((t.v[2] >> 2) & 0xff); 27 | r[14] = (unsigned char) ((t.v[2] >> 10) & 0xff); 28 | r[15] = (unsigned char) ((t.v[2] >> 18) & 0xff); 29 | r[16] = (unsigned char) ((t.v[2] >> 26) & 0xff); 30 | r[17] = (unsigned char) ((t.v[2] >> 34) & 0xff); 31 | r[18] = (unsigned char) ((t.v[2] >> 42) & 0xff); 32 | r[19] = (unsigned char) ((t.v[2] >> 50)); 33 | 34 | r[19] ^= (unsigned char) ((t.v[3] << 1) & 0xfe); 35 | r[20] = (unsigned char) ((t.v[3] >> 7) & 0xff); 36 | r[21] = (unsigned char) ((t.v[3] >> 15) & 0xff); 37 | r[22] = (unsigned char) ((t.v[3] >> 23) & 0xff); 38 | r[23] = (unsigned char) ((t.v[3] >> 31) & 0xff); 39 | r[24] = (unsigned char) ((t.v[3] >> 39) & 0xff); 40 | r[25] = (unsigned char) ((t.v[3] >> 47)); 41 | 42 | r[25] ^= (unsigned char) ((t.v[4] << 4) & 0xf0); 43 | r[26] = (unsigned char) ((t.v[4] >> 4) & 0xff); 44 | r[27] = (unsigned char) ((t.v[4] >> 12) & 0xff); 45 | r[28] = (unsigned char) ((t.v[4] >> 20) & 0xff); 46 | r[29] = (unsigned char) ((t.v[4] >> 28) & 0xff); 47 | r[30] = (unsigned char) ((t.v[4] >> 36) & 0xff); 48 | r[31] = (unsigned char) ((t.v[4] >> 44)); 49 | } 50 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-51-30k/fe25519_pow2523.c: -------------------------------------------------------------------------------- 1 | #include "fe25519.h" 2 | 3 | void fe25519_pow2523(fe25519 *r, const fe25519 *x) 4 | { 5 | fe25519 z2; 6 | fe25519 z9; 7 | fe25519 z11; 8 | fe25519 z2_5_0; 9 | fe25519 z2_10_0; 10 | fe25519 z2_20_0; 11 | fe25519 z2_50_0; 12 | fe25519 z2_100_0; 13 | fe25519 t; 14 | 15 | /* 2 */ fe25519_square(&z2,x); 16 | /* 4 */ fe25519_square(&t,&z2); 17 | /* 8 */ fe25519_square(&t,&t); 18 | /* 9 */ fe25519_mul(&z9,&t,x); 19 | /* 11 */ fe25519_mul(&z11,&z9,&z2); 20 | /* 22 */ fe25519_square(&t,&z11); 21 | /* 2^5 - 2^0 = 31 */ fe25519_mul(&z2_5_0,&t,&z9); 22 | 23 | /* 2^6 - 2^1 */ fe25519_square(&t,&z2_5_0); 24 | /* 2^10 - 2^5 */ fe25519_nsquare(&t,4); 25 | /* 2^10 - 2^0 */ fe25519_mul(&z2_10_0,&t,&z2_5_0); 26 | 27 | /* 2^11 - 2^1 */ fe25519_square(&t,&z2_10_0); 28 | /* 2^20 - 2^10 */ fe25519_nsquare(&t,9); 29 | /* 2^20 - 2^0 */ fe25519_mul(&z2_20_0,&t,&z2_10_0); 30 | 31 | /* 2^21 - 2^1 */ fe25519_square(&t,&z2_20_0); 32 | /* 2^40 - 2^20 */ fe25519_nsquare(&t,19); 33 | /* 2^40 - 2^0 */ fe25519_mul(&t,&t,&z2_20_0); 34 | 35 | /* 2^41 - 2^1 */ fe25519_square(&t,&t); 36 | /* 2^50 - 2^10 */ fe25519_nsquare(&t,9); 37 | /* 2^50 - 2^0 */ fe25519_mul(&z2_50_0,&t,&z2_10_0); 38 | 39 | /* 2^51 - 2^1 */ fe25519_square(&t,&z2_50_0); 40 | /* 2^100 - 2^50 */ fe25519_nsquare(&t,49); 41 | /* 2^100 - 2^0 */ fe25519_mul(&z2_100_0,&t,&z2_50_0); 42 | 43 | /* 2^101 - 2^1 */ fe25519_square(&t,&z2_100_0); 44 | /* 2^200 - 2^100 */ fe25519_nsquare(&t,99); 45 | /* 2^200 - 2^0 */ fe25519_mul(&t,&t,&z2_100_0); 46 | 47 | /* 2^201 - 2^1 */ fe25519_square(&t,&t); 48 | /* 2^250 - 2^50 */ fe25519_nsquare(&t,49); 49 | /* 2^250 - 2^0 */ fe25519_mul(&t,&t,&z2_50_0); 50 | 51 | /* 2^251 - 2^1 */ fe25519_square(&t,&t); 52 | /* 2^252 - 2^2 */ fe25519_square(&t,&t); 53 | /* 2^252 - 3 */ fe25519_mul(r,&t,x); 54 | } 55 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-51-30k/fe25519_setint.c: -------------------------------------------------------------------------------- 1 | #include "fe25519.h" 2 | 3 | void fe25519_setint(fe25519 *r, unsigned int v) 4 | { 5 | r->v[0] = v; 6 | r->v[1] = 0; 7 | r->v[2] = 0; 8 | r->v[3] = 0; 9 | r->v[4] = 0; 10 | } 11 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-51-30k/fe25519_sub.c: -------------------------------------------------------------------------------- 1 | #include "fe25519.h" 2 | 3 | void fe25519_sub(fe25519 *r, const fe25519 *x, const fe25519 *y) 4 | { 5 | fe25519 yt = *y; 6 | /* Not required for reduced input */ 7 | 8 | unsigned long long t; 9 | t = yt.v[0] >> 51; 10 | yt.v[0] &= 2251799813685247; 11 | yt.v[1] += t; 12 | 13 | t = yt.v[1] >> 51; 14 | yt.v[1] &= 2251799813685247; 15 | yt.v[2] += t; 16 | 17 | t = yt.v[2] >> 51; 18 | yt.v[2] &= 2251799813685247; 19 | yt.v[3] += t; 20 | 21 | t = yt.v[3] >> 51; 22 | yt.v[3] &= 2251799813685247; 23 | yt.v[4] += t; 24 | 25 | t = yt.v[4] >> 51; 26 | yt.v[4] &= 2251799813685247; 27 | yt.v[0] += 19*t; 28 | 29 | r->v[0] = x->v[0] + 0xFFFFFFFFFFFDA - yt.v[0]; 30 | r->v[1] = x->v[1] + 0xFFFFFFFFFFFFE - yt.v[1]; 31 | r->v[2] = x->v[2] + 0xFFFFFFFFFFFFE - yt.v[2]; 32 | r->v[3] = x->v[3] + 0xFFFFFFFFFFFFE - yt.v[3]; 33 | r->v[4] = x->v[4] + 0xFFFFFFFFFFFFE - yt.v[4]; 34 | } 35 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-51-30k/fe25519_unpack.c: -------------------------------------------------------------------------------- 1 | #include "fe25519.h" 2 | 3 | void fe25519_unpack(fe25519 *r, const unsigned char x[32]) 4 | { 5 | r->v[0] = x[0]; 6 | r->v[0] += (unsigned long long)x[1] << 8; 7 | r->v[0] += (unsigned long long)x[2] << 16; 8 | r->v[0] += (unsigned long long)x[3] << 24; 9 | r->v[0] += (unsigned long long)x[4] << 32; 10 | r->v[0] += (unsigned long long)x[5] << 40; 11 | r->v[0] += ((unsigned long long)x[6] & 7) << 48; 12 | 13 | r->v[1] = x[6] >> 3; 14 | r->v[1] += (unsigned long long)x[7] << 5; 15 | r->v[1] += (unsigned long long)x[8] << 13; 16 | r->v[1] += (unsigned long long)x[9] << 21; 17 | r->v[1] += (unsigned long long)x[10] << 29; 18 | r->v[1] += (unsigned long long)x[11] << 37; 19 | r->v[1] += ((unsigned long long)x[12] & 63) << 45; 20 | 21 | r->v[2] = x[12] >> 6; 22 | r->v[2] += (unsigned long long)x[13] << 2; 23 | r->v[2] += (unsigned long long)x[14] << 10; 24 | r->v[2] += (unsigned long long)x[15] << 18; 25 | r->v[2] += (unsigned long long)x[16] << 26; 26 | r->v[2] += (unsigned long long)x[17] << 34; 27 | r->v[2] += (unsigned long long)x[18] << 42; 28 | r->v[2] += ((unsigned long long)x[19] & 1) << 50; 29 | 30 | r->v[3] = x[19] >> 1; 31 | r->v[3] += (unsigned long long)x[20] << 7; 32 | r->v[3] += (unsigned long long)x[21] << 15; 33 | r->v[3] += (unsigned long long)x[22] << 23; 34 | r->v[3] += (unsigned long long)x[23] << 31; 35 | r->v[3] += (unsigned long long)x[24] << 39; 36 | r->v[3] += ((unsigned long long)x[25] & 15) << 47; 37 | 38 | r->v[4] = x[25] >> 4; 39 | r->v[4] += (unsigned long long)x[26] << 4; 40 | r->v[4] += (unsigned long long)x[27] << 12; 41 | r->v[4] += (unsigned long long)x[28] << 20; 42 | r->v[4] += (unsigned long long)x[29] << 28; 43 | r->v[4] += (unsigned long long)x[30] << 36; 44 | r->v[4] += ((unsigned long long)x[31] & 127) << 44; 45 | } 46 | 47 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-51-30k/ge25519_add.c: -------------------------------------------------------------------------------- 1 | #include "ge25519.h" 2 | 3 | void ge25519_add(ge25519_p3 *r, const ge25519_p3 *p, const ge25519_p3 *q) 4 | { 5 | ge25519_p1p1 grp1p1; 6 | ge25519_add_p1p1(&grp1p1, p, q); 7 | ge25519_p1p1_to_p3(r, &grp1p1); 8 | } 9 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-51-30k/ge25519_base.c: -------------------------------------------------------------------------------- 1 | #include "ge25519.h" 2 | 3 | /* Base point in P^3 coordinates (with Z=1) */ 4 | const ge25519 ge25519_base = {{{0x00062d608f25d51a, 0x000412a4b4f6592a, 0x00075b7171a4b31d, 0x0001ff60527118fe, 0x000216936d3cd6e5}}, 5 | {{0x0006666666666658, 0x0004cccccccccccc, 0x0001999999999999, 0x0003333333333333, 0x0006666666666666}}, 6 | {{0x0000000000000001, 0x0000000000000000, 0x0000000000000000, 0x0000000000000000, 0x0000000000000000}}, 7 | {{0x00068AB3A5B7DDA3, 0x00000EEA2A5EADBB, 0x0002AF8DF483C27E, 0x000332B375274732, 0x00067875F0FD78B7}}}; 8 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-51-30k/ge25519_double.c: -------------------------------------------------------------------------------- 1 | #include "ge25519.h" 2 | 3 | void ge25519_double(ge25519_p3 *r, const ge25519_p3 *p) 4 | { 5 | ge25519_p1p1 grp1p1; 6 | ge25519_dbl_p1p1(&grp1p1, (ge25519_p2 *)p); 7 | ge25519_p1p1_to_p3(r, &grp1p1); 8 | } 9 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-51-30k/ge25519_double_scalarmult.c: -------------------------------------------------------------------------------- 1 | #include "fe25519.h" 2 | #include "sc25519.h" 3 | #include "ge25519.h" 4 | 5 | #define S1_SWINDOWSIZE 5 6 | #define PRE1_SIZE (1<<(S1_SWINDOWSIZE-2)) 7 | #define S2_SWINDOWSIZE 7 8 | #define PRE2_SIZE (1<<(S2_SWINDOWSIZE-2)) 9 | 10 | ge25519_niels pre2[PRE2_SIZE] = { 11 | #include "ge25519_base_slide_multiples.data" 12 | }; 13 | 14 | static const fe25519 ec2d = {{1859910466990425, 932731440258426, 1072319116312658, 1815898335770999, 633789495995903}}; 15 | 16 | static void setneutral(ge25519 *r) 17 | { 18 | fe25519_setint(&r->x,0); 19 | fe25519_setint(&r->y,1); 20 | fe25519_setint(&r->z,1); 21 | fe25519_setint(&r->t,0); 22 | } 23 | 24 | /* computes [s1]p1 + [s2]p2 */ 25 | void ge25519_double_scalarmult_vartime(ge25519_p3 *r, const ge25519_p3 *p1, const sc25519 *s1, const sc25519 *s2) 26 | { 27 | signed char slide1[256], slide2[256]; 28 | ge25519_pniels pre1[PRE1_SIZE], neg; 29 | ge25519_p3 d1; 30 | ge25519_p1p1 t; 31 | ge25519_niels nneg; 32 | fe25519 d; 33 | int i; 34 | 35 | sc25519_slide(slide1, s1, S1_SWINDOWSIZE); 36 | sc25519_slide(slide2, s2, S2_SWINDOWSIZE); 37 | 38 | /* precomputation */ 39 | pre1[0] = *(ge25519_pniels *)p1; 40 | ge25519_dbl_p1p1(&t,(ge25519_p2 *)pre1); ge25519_p1p1_to_p3(&d1, &t); 41 | /* Convert pre[0] to projective Niels representation */ 42 | d = pre1[0].ysubx; 43 | fe25519_sub(&pre1[0].ysubx, &pre1[0].xaddy, &pre1[0].ysubx); 44 | fe25519_add(&pre1[0].xaddy, &pre1[0].xaddy, &d); 45 | fe25519_mul(&pre1[0].t2d, &pre1[0].t2d, &ec2d); 46 | 47 | for(i=0;i= 0;--i) { 54 | if (slide1[i] || slide2[i]) goto firstbit; 55 | } 56 | 57 | for(;i>=0;i--) 58 | { 59 | firstbit: 60 | 61 | ge25519_dbl_p1p1(&t, (ge25519_p2 *)r); 62 | 63 | if(slide1[i]>0) 64 | { 65 | ge25519_p1p1_to_p3(r, &t); 66 | ge25519_pnielsadd_p1p1(&t, r, &pre1[slide1[i]/2]); 67 | } 68 | else if(slide1[i]<0) 69 | { 70 | ge25519_p1p1_to_p3(r, &t); 71 | neg = pre1[-slide1[i]/2]; 72 | d = neg.ysubx; 73 | neg.ysubx = neg.xaddy; 74 | neg.xaddy = d; 75 | fe25519_neg(&neg.t2d, &neg.t2d); 76 | ge25519_pnielsadd_p1p1(&t, r, &neg); 77 | } 78 | 79 | if(slide2[i]>0) 80 | { 81 | ge25519_p1p1_to_p3(r, &t); 82 | ge25519_nielsadd_p1p1(&t, r, &pre2[slide2[i]/2]); 83 | } 84 | else if(slide2[i]<0) 85 | { 86 | ge25519_p1p1_to_p3(r, &t); 87 | nneg = pre2[-slide2[i]/2]; 88 | d = nneg.ysubx; 89 | nneg.ysubx = nneg.xaddy; 90 | nneg.xaddy = d; 91 | fe25519_neg(&nneg.t2d, &nneg.t2d); 92 | ge25519_nielsadd_p1p1(&t, r, &nneg); 93 | } 94 | 95 | ge25519_p1p1_to_p2((ge25519_p2 *)r, &t); 96 | } 97 | } 98 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-51-30k/ge25519_isneutral.c: -------------------------------------------------------------------------------- 1 | #include "fe25519.h" 2 | #include "ge25519.h" 3 | 4 | int ge25519_isneutral_vartime(const ge25519_p3 *p) 5 | { 6 | if(!fe25519_iszero_vartime(&p->x)) return 0; 7 | if(!fe25519_iseq_vartime(&p->y, &p->z)) return 0; 8 | return 1; 9 | } 10 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-51-30k/ge25519_multi_scalarmult.c: -------------------------------------------------------------------------------- 1 | #include "fe25519.h" 2 | #include "sc25519.h" 3 | #include "ge25519.h" 4 | #include "index_heap.h" 5 | 6 | static void setneutral(ge25519 *r) 7 | { 8 | fe25519_setint(&r->x,0); 9 | fe25519_setint(&r->y,1); 10 | fe25519_setint(&r->z,1); 11 | fe25519_setint(&r->t,0); 12 | } 13 | 14 | static void ge25519_scalarmult_vartime_2limbs(ge25519 *r, ge25519 *p, sc25519 *s) 15 | { 16 | if (s->v[1] == 0 && s->v[0] == 1) /* This will happen most of the time after Bos-Coster */ 17 | *r = *p; 18 | else if (s->v[1] == 0 && s->v[0] == 0) /* This won't ever happen, except for all scalars == 0 in Bos-Coster */ 19 | setneutral(r); 20 | else 21 | { 22 | ge25519 d; 23 | unsigned long long mask = (1ULL << 63); 24 | int i = 1; 25 | while(!(mask & s->v[1]) && mask != 0) 26 | mask >>= 1; 27 | if(mask == 0) 28 | { 29 | mask = (1ULL << 63); 30 | i = 0; 31 | while(!(mask & s->v[0]) && mask != 0) 32 | mask >>= 1; 33 | } 34 | d = *p; 35 | mask >>= 1; 36 | for(;mask != 0;mask >>= 1) 37 | { 38 | ge25519_double(&d,&d); 39 | if(s->v[i] & mask) 40 | ge25519_add(&d,&d,p); 41 | } 42 | if(i==1) 43 | { 44 | mask = (1ULL << 63); 45 | for(;mask != 0;mask >>= 1) 46 | { 47 | ge25519_double(&d,&d); 48 | if(s->v[0] & mask) 49 | ge25519_add(&d,&d,p); 50 | } 51 | } 52 | *r = d; 53 | } 54 | } 55 | 56 | /* caller's responsibility to ensure npoints >= 5 */ 57 | void ge25519_multi_scalarmult_vartime(ge25519_p3 *r, ge25519_p3 *p, sc25519 *s, const unsigned long long npoints) 58 | { 59 | unsigned long long pos[npoints]; 60 | unsigned long long hlen=((npoints+1)/2)|1; 61 | unsigned long long max1, max2,i; 62 | 63 | heap_init(pos, hlen, s); 64 | 65 | for(i=0;;i++) 66 | { 67 | heap_get2max(pos, &max1, &max2, s); 68 | if((s[max1].v[3] == 0) || (sc25519_iszero_vartime(&s[max2]))) break; 69 | sc25519_sub_nored(&s[max1],&s[max1],&s[max2]); 70 | ge25519_add(&p[max2],&p[max2],&p[max1]); 71 | heap_rootreplaced(pos, hlen, s); 72 | } 73 | for(;;i++) 74 | { 75 | heap_get2max(pos, &max1, &max2, s); 76 | if((s[max1].v[2] == 0) || (sc25519_iszero_vartime(&s[max2]))) break; 77 | sc25519_sub_nored(&s[max1],&s[max1],&s[max2]); 78 | ge25519_add(&p[max2],&p[max2],&p[max1]); 79 | heap_rootreplaced_3limbs(pos, hlen, s); 80 | } 81 | /* We know that (npoints-1)/2 scalars are only 128-bit scalars */ 82 | heap_extend(pos, hlen, npoints, s); 83 | hlen = npoints; 84 | for(;;i++) 85 | { 86 | heap_get2max(pos, &max1, &max2, s); 87 | if((s[max1].v[1] == 0) || (sc25519_iszero_vartime(&s[max2]))) break; 88 | sc25519_sub_nored(&s[max1],&s[max1],&s[max2]); 89 | ge25519_add(&p[max2],&p[max2],&p[max1]); 90 | heap_rootreplaced_2limbs(pos, hlen, s); 91 | } 92 | for(;;i++) 93 | { 94 | heap_get2max(pos, &max1, &max2, s); 95 | if(sc25519_iszero_vartime(&s[max2])) break; 96 | sc25519_sub_nored(&s[max1],&s[max1],&s[max2]); 97 | ge25519_add(&p[max2],&p[max2],&p[max1]); 98 | heap_rootreplaced_1limb(pos, hlen, s); 99 | } 100 | 101 | ge25519_scalarmult_vartime_2limbs(r, &p[max1], &s[max1]); 102 | } 103 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-51-30k/ge25519_pack.c: -------------------------------------------------------------------------------- 1 | #include "fe25519.h" 2 | #include "sc25519.h" 3 | #include "ge25519.h" 4 | 5 | void ge25519_pack(unsigned char r[32], const ge25519_p3 *p) 6 | { 7 | fe25519 tx, ty, zi; 8 | fe25519_invert(&zi, &p->z); 9 | fe25519_mul(&tx, &p->x, &zi); 10 | fe25519_mul(&ty, &p->y, &zi); 11 | fe25519_pack(r, &ty); 12 | r[31] ^= fe25519_getparity(&tx) << 7; 13 | } 14 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-51-30k/ge25519_scalarmult_base.c: -------------------------------------------------------------------------------- 1 | #include "fe25519.h" 2 | #include "sc25519.h" 3 | #include "ge25519.h" 4 | 5 | /* Multiples of the base point in Niels' representation */ 6 | static const ge25519_niels ge25519_base_multiples_niels[] = { 7 | #include "ge25519_base_niels_smalltables.data" 8 | }; 9 | 10 | /* d */ 11 | static const fe25519 ecd = {{929955233495203, 466365720129213, 1662059464998953, 2033849074728123, 1442794654840575}}; 12 | 13 | void ge25519_scalarmult_base(ge25519_p3 *r, const sc25519 *s) 14 | { 15 | signed char b[64]; 16 | int i; 17 | ge25519_niels t; 18 | fe25519 d; 19 | 20 | sc25519_window4(b,s); 21 | 22 | ge25519_p1p1 tp1p1; 23 | choose_t((ge25519_niels *)r, 0, (signed long long) b[1], ge25519_base_multiples_niels); 24 | fe25519_sub(&d, &r->y, &r->x); 25 | fe25519_add(&r->y, &r->y, &r->x); 26 | r->x = d; 27 | r->t = r->z; 28 | fe25519_setint(&r->z,2); 29 | for(i=3;i<64;i+=2) 30 | { 31 | choose_t(&t, (unsigned long long) i/2, (signed long long) b[i], ge25519_base_multiples_niels); 32 | ge25519_nielsadd2(r, &t); 33 | } 34 | ge25519_dbl_p1p1(&tp1p1,(ge25519_p2 *)r); 35 | ge25519_p1p1_to_p2((ge25519_p2 *)r, &tp1p1); 36 | ge25519_dbl_p1p1(&tp1p1,(ge25519_p2 *)r); 37 | ge25519_p1p1_to_p2((ge25519_p2 *)r, &tp1p1); 38 | ge25519_dbl_p1p1(&tp1p1,(ge25519_p2 *)r); 39 | ge25519_p1p1_to_p2((ge25519_p2 *)r, &tp1p1); 40 | ge25519_dbl_p1p1(&tp1p1,(ge25519_p2 *)r); 41 | ge25519_p1p1_to_p3(r, &tp1p1); 42 | choose_t(&t, (unsigned long long) 0, (signed long long) b[0], ge25519_base_multiples_niels); 43 | fe25519_mul(&t.t2d, &t.t2d, &ecd); 44 | ge25519_nielsadd2(r, &t); 45 | for(i=2;i<64;i+=2) 46 | { 47 | choose_t(&t, (unsigned long long) i/2, (signed long long) b[i], ge25519_base_multiples_niels); 48 | ge25519_nielsadd2(r, &t); 49 | } 50 | } 51 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-51-30k/ge25519_unpackneg.c: -------------------------------------------------------------------------------- 1 | #include "fe25519.h" 2 | #include "ge25519.h" 3 | 4 | /* d */ 5 | static const fe25519 ecd = {{929955233495203, 466365720129213, 1662059464998953, 2033849074728123, 1442794654840575}}; 6 | /* sqrt(-1) */ 7 | static const fe25519 sqrtm1 = {{1718705420411056, 234908883556509, 2233514472574048, 2117202627021982, 765476049583133}}; 8 | 9 | /* return 0 on success, -1 otherwise */ 10 | int ge25519_unpackneg_vartime(ge25519_p3 *r, const unsigned char p[32]) 11 | { 12 | fe25519 t, chk, num, den, den2, den4, den6; 13 | unsigned char par = p[31] >> 7; 14 | 15 | fe25519_setint(&r->z,1); 16 | fe25519_unpack(&r->y, p); 17 | fe25519_square(&num, &r->y); /* x = y^2 */ 18 | fe25519_mul(&den, &num, &ecd); /* den = dy^2 */ 19 | fe25519_sub(&num, &num, &r->z); /* x = y^2-1 */ 20 | fe25519_add(&den, &r->z, &den); /* den = dy^2+1 */ 21 | 22 | /* Computation of sqrt(num/den) 23 | 1.: computation of num^((p-5)/8)*den^((7p-35)/8) = (num*den^7)^((p-5)/8) 24 | */ 25 | fe25519_square(&den2, &den); 26 | fe25519_square(&den4, &den2); 27 | fe25519_mul(&den6, &den4, &den2); 28 | fe25519_mul(&t, &den6, &num); 29 | fe25519_mul(&t, &t, &den); 30 | 31 | fe25519_pow2523(&t, &t); 32 | /* 2. computation of r->x = t * num * den^3 33 | */ 34 | fe25519_mul(&t, &t, &num); 35 | fe25519_mul(&t, &t, &den); 36 | fe25519_mul(&t, &t, &den); 37 | fe25519_mul(&r->x, &t, &den); 38 | 39 | /* 3. Check whether sqrt computation gave correct result, multiply by sqrt(-1) if not: 40 | */ 41 | fe25519_square(&chk, &r->x); 42 | fe25519_mul(&chk, &chk, &den); 43 | if (!fe25519_iseq_vartime(&chk, &num)) 44 | fe25519_mul(&r->x, &r->x, &sqrtm1); 45 | 46 | /* 4. Now we have one of the two square roots, except if input was not a square 47 | */ 48 | fe25519_square(&chk, &r->x); 49 | fe25519_mul(&chk, &chk, &den); 50 | if (!fe25519_iseq_vartime(&chk, &num)) 51 | return -1; 52 | 53 | /* 5. Choose the desired square root according to parity: 54 | */ 55 | if(fe25519_getparity(&r->x) != (1-par)) 56 | fe25519_neg(&r->x, &r->x); 57 | 58 | fe25519_mul(&r->t, &r->x, &r->y); 59 | return 0; 60 | } 61 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-51-30k/hram.c: -------------------------------------------------------------------------------- 1 | #include "crypto_hash_sha512.h" 2 | #include "hram.h" 3 | 4 | void get_hram(unsigned char *hram, const unsigned char *sm, const unsigned char *pk, unsigned char *playground, unsigned long long smlen) 5 | { 6 | unsigned long long i; 7 | 8 | for (i = 0;i < 32;++i) playground[i] = sm[i]; 9 | for (i = 32;i < 64;++i) playground[i] = pk[i-32]; 10 | for (i = 64;i < smlen;++i) playground[i] = sm[i]; 11 | 12 | crypto_hash_sha512(hram,playground,smlen); 13 | } 14 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-51-30k/hram.h: -------------------------------------------------------------------------------- 1 | #ifndef HRAM_H 2 | #define HRAM_H 3 | 4 | #define get_hram crypto_sign_ed25519_amd64_51_30k_batch_get_hram 5 | 6 | extern void get_hram(unsigned char *hram, const unsigned char *sm, const unsigned char *pk, unsigned char *playground, unsigned long long smlen); 7 | 8 | #endif 9 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-51-30k/implementors: -------------------------------------------------------------------------------- 1 | Daniel J. Bernstein 2 | Niels Duif 3 | Tanja Lange 4 | lead: Peter Schwabe 5 | Bo-Yin Yang 6 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-51-30k/index_heap.c: -------------------------------------------------------------------------------- 1 | #include "sc25519.h" 2 | #include "index_heap.h" 3 | 4 | /* caller's responsibility to ensure hlen>=3 */ 5 | void heap_init(unsigned long long *h, unsigned long long hlen, sc25519 *scalars) 6 | { 7 | h[0] = 0; 8 | unsigned long long i=1; 9 | while(i 0) 30 | { 31 | /* if(sc25519_lt_vartime(&scalars[h[ppos]], &scalars[h[pos]])) */ 32 | if(sc25519_lt(&scalars[h[ppos]], &scalars[h[pos]])) 33 | { 34 | t = h[ppos]; 35 | h[ppos] = h[pos]; 36 | h[pos] = t; 37 | pos = ppos; 38 | ppos = (pos-1)/2; 39 | } 40 | else break; 41 | } 42 | (*hlen)++; 43 | } 44 | 45 | /* Put the largest value in the heap in max1, the second largest in max2 */ 46 | void heap_get2max(unsigned long long *h, unsigned long long *max1, unsigned long long *max2, sc25519 *scalars) 47 | { 48 | *max1 = h[0]; 49 | *max2 = h[1]; 50 | if(sc25519_lt(&scalars[h[1]],&scalars[h[2]])) 51 | *max2 = h[2]; 52 | } 53 | 54 | /* After the root has been replaced, restore heap property */ 55 | /* extern void heap_rootreplaced(unsigned long long *h, unsigned long long hlen, sc25519 *scalars); 56 | */ 57 | /* extern void heap_rootreplaced_shortscalars(unsigned long long *h, unsigned long long hlen, sc25519 *scalars); 58 | */ 59 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-51-30k/index_heap.h: -------------------------------------------------------------------------------- 1 | #ifndef INDEX_HEAP_H 2 | #define INDEX_HEAP_H 3 | 4 | #include "sc25519.h" 5 | 6 | #define heap_init crypto_sign_ed25519_amd64_51_30k_batch_heap_init 7 | #define heap_extend crypto_sign_ed25519_amd64_51_30k_batch_heap_extend 8 | #define heap_pop crypto_sign_ed25519_amd64_51_30k_batch_heap_pop 9 | #define heap_push crypto_sign_ed25519_amd64_51_30k_batch_heap_push 10 | #define heap_get2max crypto_sign_ed25519_amd64_51_30k_batch_heap_get2max 11 | #define heap_rootreplaced crypto_sign_ed25519_amd64_51_30k_batch_heap_rootreplaced 12 | #define heap_rootreplaced_3limbs crypto_sign_ed25519_amd64_51_30k_batch_heap_rootreplaced_3limbs 13 | #define heap_rootreplaced_2limbs crypto_sign_ed25519_amd64_51_30k_batch_heap_rootreplaced_2limbs 14 | #define heap_rootreplaced_1limb crypto_sign_ed25519_amd64_51_30k_batch_heap_rootreplaced_1limb 15 | 16 | void heap_init(unsigned long long *h, unsigned long long hlen, sc25519 *scalars); 17 | 18 | void heap_extend(unsigned long long *h, unsigned long long oldlen, unsigned long long newlen, sc25519 *scalars); 19 | 20 | unsigned long long heap_pop(unsigned long long *h, unsigned long long *hlen, sc25519 *scalars); 21 | 22 | void heap_push(unsigned long long *h, unsigned long long *hlen, unsigned long long elem, sc25519 *scalars); 23 | 24 | void heap_get2max(unsigned long long *h, unsigned long long *max1, unsigned long long *max2, sc25519 *scalars); 25 | 26 | void heap_rootreplaced(unsigned long long *h, unsigned long long hlen, sc25519 *scalars); 27 | void heap_rootreplaced_3limbs(unsigned long long *h, unsigned long long hlen, sc25519 *scalars); 28 | void heap_rootreplaced_2limbs(unsigned long long *h, unsigned long long hlen, sc25519 *scalars); 29 | void heap_rootreplaced_1limb(unsigned long long *h, unsigned long long hlen, sc25519 *scalars); 30 | 31 | #endif 32 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-51-30k/keypair.c: -------------------------------------------------------------------------------- 1 | #include 2 | #include "crypto_sign.h" 3 | #include "crypto_hash_sha512.h" 4 | #include "randombytes.h" 5 | #include "ge25519.h" 6 | 7 | int crypto_sign_keypair(unsigned char *pk,unsigned char *sk) 8 | { 9 | unsigned char az[64]; 10 | sc25519 scsk; 11 | ge25519 gepk; 12 | 13 | randombytes(sk,32); 14 | crypto_hash_sha512(az,sk,32); 15 | az[0] &= 248; 16 | az[31] &= 127; 17 | az[31] |= 64; 18 | 19 | sc25519_from32bytes(&scsk,az); 20 | 21 | ge25519_scalarmult_base(&gepk, &scsk); 22 | ge25519_pack(pk, &gepk); 23 | memmove(sk + 32,pk,32); 24 | return 0; 25 | } 26 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-51-30k/open.c: -------------------------------------------------------------------------------- 1 | #include 2 | #include "crypto_sign.h" 3 | #include "crypto_verify_32.h" 4 | #include "crypto_hash_sha512.h" 5 | #include "ge25519.h" 6 | 7 | int crypto_sign_open( 8 | unsigned char *m,unsigned long long *mlen, 9 | const unsigned char *sm,unsigned long long smlen, 10 | const unsigned char *pk 11 | ) 12 | { 13 | unsigned char pkcopy[32]; 14 | unsigned char rcopy[32]; 15 | unsigned char hram[64]; 16 | unsigned char rcheck[32]; 17 | ge25519 get1, get2; 18 | sc25519 schram, scs; 19 | 20 | if (smlen < 64) goto badsig; 21 | if (sm[63] & 224) goto badsig; 22 | if (ge25519_unpackneg_vartime(&get1,pk)) goto badsig; 23 | 24 | memmove(pkcopy,pk,32); 25 | memmove(rcopy,sm,32); 26 | 27 | sc25519_from32bytes(&scs, sm+32); 28 | 29 | memmove(m,sm,smlen); 30 | memmove(m + 32,pkcopy,32); 31 | crypto_hash_sha512(hram,m,smlen); 32 | 33 | sc25519_from64bytes(&schram, hram); 34 | 35 | ge25519_double_scalarmult_vartime(&get2, &get1, &schram, &scs); 36 | ge25519_pack(rcheck, &get2); 37 | 38 | if (crypto_verify_32(rcopy,rcheck) == 0) { 39 | memmove(m,m + 64,smlen - 64); 40 | memset(m + smlen - 64,0,64); 41 | *mlen = smlen - 64; 42 | return 0; 43 | } 44 | 45 | badsig: 46 | *mlen = (unsigned long long) -1; 47 | memset(m,0,smlen); 48 | return -1; 49 | } 50 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-51-30k/sc25519.h: -------------------------------------------------------------------------------- 1 | #ifndef SC25519_H 2 | #define SC25519_H 3 | 4 | #define sc25519 crypto_sign_ed25519_amd64_51_30k_batch_sc25519 5 | #define shortsc25519 crypto_sign_ed25519_amd64_51_30k_batch_shortsc25519 6 | #define sc25519_from32bytes crypto_sign_ed25519_amd64_51_30k_batch_sc25519_from32bytes 7 | #define shortsc25519_from16bytes crypto_sign_ed25519_amd64_51_30k_batch_shortsc25519_from16bytes 8 | #define sc25519_from64bytes crypto_sign_ed25519_amd64_51_30k_batch_sc25519_from64bytes 9 | #define sc25519_from_shortsc crypto_sign_ed25519_amd64_51_30k_batch_sc25519_from_shortsc 10 | #define sc25519_to32bytes crypto_sign_ed25519_amd64_51_30k_batch_sc25519_to32bytes 11 | #define sc25519_iszero_vartime crypto_sign_ed25519_amd64_51_30k_batch_sc25519_iszero_vartime 12 | #define sc25519_isshort_vartime crypto_sign_ed25519_amd64_51_30k_batch_sc25519_isshort_vartime 13 | #define sc25519_lt crypto_sign_ed25519_amd64_51_30k_batch_sc25519_lt 14 | #define sc25519_add crypto_sign_ed25519_amd64_51_30k_batch_sc25519_add 15 | #define sc25519_sub_nored crypto_sign_ed25519_amd64_51_30k_batch_sc25519_sub_nored 16 | #define sc25519_mul crypto_sign_ed25519_amd64_51_30k_batch_sc25519_mul 17 | #define sc25519_mul_shortsc crypto_sign_ed25519_amd64_51_30k_batch_sc25519_mul_shortsc 18 | #define sc25519_window4 crypto_sign_ed25519_amd64_51_30k_batch_sc25519_window4 19 | #define sc25519_window5 crypto_sign_ed25519_amd64_51_30k_batch_sc25519_window5 20 | #define sc25519_slide crypto_sign_ed25519_amd64_51_30k_batch_sc25519_slide 21 | #define sc25519_2interleave2 crypto_sign_ed25519_amd64_51_30k_batch_sc25519_2interleave2 22 | #define sc25519_barrett crypto_sign_ed25519_amd64_51_30k_batch_sc25519_barrett 23 | 24 | typedef struct 25 | { 26 | unsigned long long v[4]; 27 | } 28 | sc25519; 29 | 30 | typedef struct 31 | { 32 | unsigned long long v[2]; 33 | } 34 | shortsc25519; 35 | 36 | void sc25519_from32bytes(sc25519 *r, const unsigned char x[32]); 37 | 38 | void sc25519_from64bytes(sc25519 *r, const unsigned char x[64]); 39 | 40 | void sc25519_from_shortsc(sc25519 *r, const shortsc25519 *x); 41 | 42 | void sc25519_to32bytes(unsigned char r[32], const sc25519 *x); 43 | 44 | int sc25519_iszero_vartime(const sc25519 *x); 45 | 46 | int sc25519_lt(const sc25519 *x, const sc25519 *y); 47 | 48 | void sc25519_add(sc25519 *r, const sc25519 *x, const sc25519 *y); 49 | 50 | void sc25519_sub_nored(sc25519 *r, const sc25519 *x, const sc25519 *y); 51 | 52 | void sc25519_mul(sc25519 *r, const sc25519 *x, const sc25519 *y); 53 | 54 | void sc25519_mul_shortsc(sc25519 *r, const sc25519 *x, const shortsc25519 *y); 55 | 56 | /* Convert s into a representation of the form \sum_{i=0}^{63}r[i]2^(4*i) 57 | * with r[i] in {-8,...,7} 58 | */ 59 | void sc25519_window4(signed char r[64], const sc25519 *s); 60 | 61 | void sc25519_window5(signed char r[51], const sc25519 *s); 62 | 63 | void sc25519_slide(signed char r[256], const sc25519 *s, int swindowsize); 64 | 65 | void sc25519_2interleave2(unsigned char r[127], const sc25519 *s1, const sc25519 *s2); 66 | 67 | void sc25519_barrett(sc25519 *r, unsigned long long x[8]); 68 | 69 | #endif 70 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-51-30k/sc25519_from32bytes.c: -------------------------------------------------------------------------------- 1 | #include "sc25519.h" 2 | 3 | /*Arithmetic modulo the group order n = 2^252 + 27742317777372353535851937790883648493 4 | * = 7237005577332262213973186563042994240857116359379907606001950938285454250989 5 | */ 6 | 7 | /* Contains order, 2*order, 4*order, 8*order, each represented in 4 consecutive unsigned long long */ 8 | static const unsigned long long order[16] = {0x5812631A5CF5D3EDULL, 0x14DEF9DEA2F79CD6ULL, 9 | 0x0000000000000000ULL, 0x1000000000000000ULL, 10 | 0xB024C634B9EBA7DAULL, 0x29BDF3BD45EF39ACULL, 11 | 0x0000000000000000ULL, 0x2000000000000000ULL, 12 | 0x60498C6973D74FB4ULL, 0x537BE77A8BDE7359ULL, 13 | 0x0000000000000000ULL, 0x4000000000000000ULL, 14 | 0xC09318D2E7AE9F68ULL, 0xA6F7CEF517BCE6B2ULL, 15 | 0x0000000000000000ULL, 0x8000000000000000ULL}; 16 | 17 | static unsigned long long smaller(unsigned long long a,unsigned long long b) 18 | { 19 | unsigned long long atop = a >> 32; 20 | unsigned long long abot = a & 4294967295; 21 | unsigned long long btop = b >> 32; 22 | unsigned long long bbot = b & 4294967295; 23 | unsigned long long atopbelowbtop = (atop - btop) >> 63; 24 | unsigned long long atopeqbtop = ((atop ^ btop) - 1) >> 63; 25 | unsigned long long abotbelowbbot = (abot - bbot) >> 63; 26 | return atopbelowbtop | (atopeqbtop & abotbelowbbot); 27 | } 28 | 29 | void sc25519_from32bytes(sc25519 *r, const unsigned char x[32]) 30 | { 31 | unsigned long long t[4]; 32 | unsigned long long b; 33 | unsigned long long mask; 34 | int i, j; 35 | 36 | /* assuming little-endian */ 37 | r->v[0] = *(unsigned long long *)x; 38 | r->v[1] = *(((unsigned long long *)x)+1); 39 | r->v[2] = *(((unsigned long long *)x)+2); 40 | r->v[3] = *(((unsigned long long *)x)+3); 41 | 42 | for(j=3;j>=0;j--) 43 | { 44 | b=0; 45 | for(i=0;i<4;i++) 46 | { 47 | b += order[4*j+i]; /* no overflow for this particular order */ 48 | t[i] = r->v[i] - b; 49 | b = smaller(r->v[i],b); 50 | } 51 | mask = b - 1; 52 | for(i=0;i<4;i++) 53 | r->v[i] ^= mask & (r->v[i] ^ t[i]); 54 | } 55 | } 56 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-51-30k/sc25519_from64bytes.c: -------------------------------------------------------------------------------- 1 | #include "sc25519.h" 2 | 3 | void sc25519_from64bytes(sc25519 *r, const unsigned char x[64]) 4 | { 5 | /* assuming little-endian representation of unsigned long long */ 6 | sc25519_barrett(r, (unsigned long long *)x); 7 | } 8 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-51-30k/sc25519_from_shortsc.c: -------------------------------------------------------------------------------- 1 | #include "sc25519.h" 2 | 3 | void sc25519_from_shortsc(sc25519 *r, const shortsc25519 *x) 4 | { 5 | r->v[0] = x->v[0]; 6 | r->v[1] = x->v[1]; 7 | r->v[2] = 0; 8 | r->v[3] = 0; 9 | } 10 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-51-30k/sc25519_iszero.c: -------------------------------------------------------------------------------- 1 | #include "sc25519.h" 2 | 3 | int sc25519_iszero_vartime(const sc25519 *x) 4 | { 5 | if(x->v[0] != 0) return 0; 6 | if(x->v[1] != 0) return 0; 7 | if(x->v[2] != 0) return 0; 8 | if(x->v[3] != 0) return 0; 9 | return 1; 10 | } 11 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-51-30k/sc25519_lt.s: -------------------------------------------------------------------------------- 1 | 2 | # qhasm: int64 xp 3 | 4 | # qhasm: int64 yp 5 | 6 | # qhasm: int64 ret 7 | 8 | # qhasm: input xp 9 | 10 | # qhasm: input yp 11 | 12 | # qhasm: output ret 13 | 14 | # qhasm: int64 t0 15 | 16 | # qhasm: int64 t1 17 | 18 | # qhasm: int64 t2 19 | 20 | # qhasm: int64 t3 21 | 22 | # qhasm: int64 doof 23 | 24 | # qhasm: int64 caller1 25 | 26 | # qhasm: int64 caller2 27 | 28 | # qhasm: int64 caller3 29 | 30 | # qhasm: int64 caller4 31 | 32 | # qhasm: int64 caller5 33 | 34 | # qhasm: int64 caller6 35 | 36 | # qhasm: int64 caller7 37 | 38 | # qhasm: caller caller1 39 | 40 | # qhasm: caller caller2 41 | 42 | # qhasm: caller caller3 43 | 44 | # qhasm: caller caller4 45 | 46 | # qhasm: caller caller5 47 | 48 | # qhasm: caller caller6 49 | 50 | # qhasm: caller caller7 51 | 52 | # qhasm: stack64 caller4_stack 53 | 54 | # qhasm: stack64 caller5_stack 55 | 56 | # qhasm: stack64 caller6_stack 57 | 58 | # qhasm: stack64 caller7_stack 59 | 60 | # qhasm: enter crypto_sign_ed25519_amd64_51_30k_batch_sc25519_lt 61 | .text 62 | .p2align 5 63 | .globl _crypto_sign_ed25519_amd64_51_30k_batch_sc25519_lt 64 | .globl crypto_sign_ed25519_amd64_51_30k_batch_sc25519_lt 65 | _crypto_sign_ed25519_amd64_51_30k_batch_sc25519_lt: 66 | crypto_sign_ed25519_amd64_51_30k_batch_sc25519_lt: 67 | mov %rsp,%r11 68 | and $31,%r11 69 | add $0,%r11 70 | sub %r11,%rsp 71 | 72 | # qhasm: t0 = *(uint64 *)(xp + 0) 73 | # asm 1: movq 0(t0=int64#3 74 | # asm 2: movq 0(t0=%rdx 75 | movq 0(%rdi),%rdx 76 | 77 | # qhasm: t1 = *(uint64 *)(xp + 8) 78 | # asm 1: movq 8(t1=int64#4 79 | # asm 2: movq 8(t1=%rcx 80 | movq 8(%rdi),%rcx 81 | 82 | # qhasm: t2 = *(uint64 *)(xp + 16) 83 | # asm 1: movq 16(t2=int64#5 84 | # asm 2: movq 16(t2=%r8 85 | movq 16(%rdi),%r8 86 | 87 | # qhasm: t3 = *(uint64 *)(xp + 24) 88 | # asm 1: movq 24(t3=int64#1 89 | # asm 2: movq 24(t3=%rdi 90 | movq 24(%rdi),%rdi 91 | 92 | # qhasm: carry? t0 -= *(uint64 *)(yp + 0) 93 | # asm 1: subq 0(ret=int64#1 114 | # asm 2: mov $0,>ret=%rdi 115 | mov $0,%rdi 116 | 117 | # qhasm: doof = 1 118 | # asm 1: mov $1,>doof=int64#2 119 | # asm 2: mov $1,>doof=%rsi 120 | mov $1,%rsi 121 | 122 | # qhasm: ret = doof if carry 123 | # asm 1: cmovc v, y->v); 11 | sc25519_barrett(r, t); 12 | } 13 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-51-30k/sc25519_mul_shortsc.c: -------------------------------------------------------------------------------- 1 | #include "sc25519.h" 2 | 3 | void sc25519_mul_shortsc(sc25519 *r, const sc25519 *x, const shortsc25519 *y) 4 | { 5 | /* XXX: This wants to be faster */ 6 | sc25519 t; 7 | sc25519_from_shortsc(&t, y); 8 | sc25519_mul(r, x, &t); 9 | } 10 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-51-30k/sc25519_slide.c: -------------------------------------------------------------------------------- 1 | #include "sc25519.h" 2 | 3 | void sc25519_slide(signed char r[256], const sc25519 *s, int swindowsize) 4 | { 5 | int i,j,k,b,m=(1<<(swindowsize-1))-1, soplen=256; 6 | unsigned long long sv0 = s->v[0]; 7 | unsigned long long sv1 = s->v[1]; 8 | unsigned long long sv2 = s->v[2]; 9 | unsigned long long sv3 = s->v[3]; 10 | 11 | /* first put the binary expansion into r */ 12 | for(i=0;i<64;i++) { 13 | r[i] = sv0 & 1; 14 | r[i+64] = sv1 & 1; 15 | r[i+128] = sv2 & 1; 16 | r[i+192] = sv3 & 1; 17 | sv0 >>= 1; 18 | sv1 >>= 1; 19 | sv2 >>= 1; 20 | sv3 >>= 1; 21 | } 22 | 23 | /* Making it sliding window */ 24 | for (j = 0;j < soplen;++j) 25 | { 26 | if (r[j]) { 27 | for (b = 1;b < soplen - j && b <= 6;++b) { 28 | if (r[j] + (r[j + b] << b) <= m) 29 | { 30 | r[j] += r[j + b] << b; r[j + b] = 0; 31 | } 32 | else if (r[j] - (r[j + b] << b) >= -m) 33 | { 34 | r[j] -= r[j + b] << b; 35 | for (k = j + b;k < soplen;++k) 36 | { 37 | if (!r[k]) { 38 | r[k] = 1; 39 | break; 40 | } 41 | r[k] = 0; 42 | } 43 | } 44 | else if (r[j + b]) 45 | break; 46 | } 47 | } 48 | } 49 | } 50 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-51-30k/sc25519_to32bytes.c: -------------------------------------------------------------------------------- 1 | #include "sc25519.h" 2 | 3 | void sc25519_to32bytes(unsigned char r[32], const sc25519 *x) 4 | { 5 | /* assuming little-endian */ 6 | int i; 7 | for(i=0;i<32;i++) r[i] = i[(unsigned char *)x->v]; 8 | } 9 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-51-30k/sc25519_window4.c: -------------------------------------------------------------------------------- 1 | #include "sc25519.h" 2 | 3 | void sc25519_window4(signed char r[64], const sc25519 *s) 4 | { 5 | char carry; 6 | int i; 7 | for(i=0;i<16;i++) 8 | r[i] = (s->v[0] >> (4*i)) & 15; 9 | for(i=0;i<16;i++) 10 | r[i+16] = (s->v[1] >> (4*i)) & 15; 11 | for(i=0;i<16;i++) 12 | r[i+32] = (s->v[2] >> (4*i)) & 15; 13 | for(i=0;i<16;i++) 14 | r[i+48] = (s->v[3] >> (4*i)) & 15; 15 | 16 | /* Making it signed */ 17 | carry = 0; 18 | for(i=0;i<63;i++) 19 | { 20 | r[i] += carry; 21 | r[i+1] += r[i] >> 4; 22 | r[i] &= 15; 23 | carry = r[i] >> 3; 24 | r[i] -= carry << 4; 25 | } 26 | r[63] += carry; 27 | } 28 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-51-30k/sign.c: -------------------------------------------------------------------------------- 1 | #include 2 | #include "crypto_sign.h" 3 | #include "crypto_hash_sha512.h" 4 | #include "ge25519.h" 5 | 6 | int crypto_sign( 7 | unsigned char *sm,unsigned long long *smlen, 8 | const unsigned char *m,unsigned long long mlen, 9 | const unsigned char *sk 10 | ) 11 | { 12 | unsigned char pk[32]; 13 | unsigned char az[64]; 14 | unsigned char nonce[64]; 15 | unsigned char hram[64]; 16 | sc25519 sck, scs, scsk; 17 | ge25519 ger; 18 | 19 | memmove(pk,sk + 32,32); 20 | /* pk: 32-byte public key A */ 21 | 22 | crypto_hash_sha512(az,sk,32); 23 | az[0] &= 248; 24 | az[31] &= 127; 25 | az[31] |= 64; 26 | /* az: 32-byte scalar a, 32-byte randomizer z */ 27 | 28 | *smlen = mlen + 64; 29 | memmove(sm + 64,m,mlen); 30 | memmove(sm + 32,az + 32,32); 31 | /* sm: 32-byte uninit, 32-byte z, mlen-byte m */ 32 | 33 | crypto_hash_sha512(nonce, sm+32, mlen+32); 34 | /* nonce: 64-byte H(z,m) */ 35 | 36 | sc25519_from64bytes(&sck, nonce); 37 | ge25519_scalarmult_base(&ger, &sck); 38 | ge25519_pack(sm, &ger); 39 | /* sm: 32-byte R, 32-byte z, mlen-byte m */ 40 | 41 | memmove(sm + 32,pk,32); 42 | /* sm: 32-byte R, 32-byte A, mlen-byte m */ 43 | 44 | crypto_hash_sha512(hram,sm,mlen + 64); 45 | /* hram: 64-byte H(R,A,m) */ 46 | 47 | sc25519_from64bytes(&scs, hram); 48 | sc25519_from32bytes(&scsk, az); 49 | sc25519_mul(&scs, &scs, &scsk); 50 | sc25519_add(&scs, &scs, &sck); 51 | /* scs: S = nonce + H(R,A,m)a */ 52 | 53 | sc25519_to32bytes(sm + 32,&scs); 54 | /* sm: 32-byte R, 32-byte S, mlen-byte m */ 55 | 56 | return 0; 57 | } 58 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-64-24k/api.h: -------------------------------------------------------------------------------- 1 | #define CRYPTO_SECRETKEYBYTES 64 2 | #define CRYPTO_PUBLICKEYBYTES 32 3 | #define CRYPTO_BYTES 64 4 | #define CRYPTO_DETERMINISTIC 1 5 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-64-24k/architectures: -------------------------------------------------------------------------------- 1 | amd64 2 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-64-24k/batch.c: -------------------------------------------------------------------------------- 1 | #include "crypto_sign.h" 2 | 3 | #include "crypto_verify_32.h" 4 | #include "crypto_hash_sha512.h" 5 | #include "randombytes.h" 6 | 7 | #include "ge25519.h" 8 | #include "hram.h" 9 | 10 | #define MAXBATCH 64 11 | 12 | int crypto_sign_open_batch( 13 | unsigned char* const m[],unsigned long long mlen[], 14 | unsigned char* const sm[],const unsigned long long smlen[], 15 | unsigned char* const pk[], 16 | unsigned long long num 17 | ) 18 | { 19 | int ret = 0; 20 | unsigned long long i, j; 21 | shortsc25519 r[MAXBATCH]; 22 | sc25519 scalars[2*MAXBATCH+1]; 23 | ge25519 points[2*MAXBATCH+1]; 24 | unsigned char hram[crypto_hash_sha512_BYTES]; 25 | unsigned long long batchsize; 26 | 27 | for (i = 0;i < num;++i) mlen[i] = -1; 28 | 29 | while (num >= 3) { 30 | batchsize = num; 31 | if (batchsize > MAXBATCH) batchsize = MAXBATCH; 32 | 33 | for (i = 0;i < batchsize;++i) 34 | if (smlen[i] < 64) goto fallback; 35 | 36 | randombytes((unsigned char*)r,sizeof(shortsc25519) * batchsize); 37 | 38 | /* Computing scalars[0] = ((r1s1 + r2s2 + ...)) */ 39 | for(i=0;iv[0] = v; 6 | r->v[1] = 0; 7 | r->v[2] = 0; 8 | r->v[3] = 0; 9 | } 10 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-64-24k/fe25519_unpack.c: -------------------------------------------------------------------------------- 1 | #include "fe25519.h" 2 | 3 | void fe25519_unpack(fe25519 *r, const unsigned char x[32]) 4 | { 5 | /* assuming little-endian */ 6 | r->v[0] = *(unsigned long long *)x; 7 | r->v[1] = *(((unsigned long long *)x)+1); 8 | r->v[2] = *(((unsigned long long *)x)+2); 9 | r->v[3] = *(((unsigned long long *)x)+3); 10 | r->v[3] &= 0x7fffffffffffffffULL; 11 | } 12 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-64-24k/ge25519_add.c: -------------------------------------------------------------------------------- 1 | #include "ge25519.h" 2 | 3 | void ge25519_add(ge25519_p3 *r, const ge25519_p3 *p, const ge25519_p3 *q) 4 | { 5 | ge25519_p1p1 grp1p1; 6 | ge25519_add_p1p1(&grp1p1, p, q); 7 | ge25519_p1p1_to_p3(r, &grp1p1); 8 | } 9 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-64-24k/ge25519_base.c: -------------------------------------------------------------------------------- 1 | #include "ge25519.h" 2 | 3 | const ge25519 ge25519_base = {{{0xC9562D608F25D51A, 0x692CC7609525A7B2, 0xC0A4E231FDD6DC5C, 0x216936D3CD6E53FE}}, 4 | {{0x6666666666666658, 0x6666666666666666, 0x6666666666666666, 0x6666666666666666}}, 5 | {{0x0000000000000001, 0x0000000000000000, 0x0000000000000000, 000000000000000000}}, 6 | {{0x6DDE8AB3A5B7DDA3, 0x20F09F80775152F5, 0x66EA4E8E64ABE37D, 0x67875F0FD78B7665}}}; 7 | 8 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-64-24k/ge25519_double.c: -------------------------------------------------------------------------------- 1 | #include "ge25519.h" 2 | 3 | void ge25519_double(ge25519_p3 *r, const ge25519_p3 *p) 4 | { 5 | ge25519_p1p1 grp1p1; 6 | ge25519_dbl_p1p1(&grp1p1, (ge25519_p2 *)p); 7 | ge25519_p1p1_to_p3(r, &grp1p1); 8 | } 9 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-64-24k/ge25519_double_scalarmult.c: -------------------------------------------------------------------------------- 1 | #include "fe25519.h" 2 | #include "sc25519.h" 3 | #include "ge25519.h" 4 | 5 | #define S1_SWINDOWSIZE 5 6 | #define PRE1_SIZE (1<<(S1_SWINDOWSIZE-2)) 7 | #define S2_SWINDOWSIZE 7 8 | #define PRE2_SIZE (1<<(S2_SWINDOWSIZE-2)) 9 | 10 | ge25519_niels pre2[PRE2_SIZE] = { 11 | #include "ge25519_base_slide_multiples.data" 12 | }; 13 | 14 | static const fe25519 ec2d = {{0xEBD69B9426B2F146, 0x00E0149A8283B156, 0x198E80F2EEF3D130, 0xA406D9DC56DFFCE7}}; 15 | 16 | static void setneutral(ge25519 *r) 17 | { 18 | fe25519_setint(&r->x,0); 19 | fe25519_setint(&r->y,1); 20 | fe25519_setint(&r->z,1); 21 | fe25519_setint(&r->t,0); 22 | } 23 | 24 | /* computes [s1]p1 + [s2]p2 */ 25 | void ge25519_double_scalarmult_vartime(ge25519_p3 *r, const ge25519_p3 *p1, const sc25519 *s1, const sc25519 *s2) 26 | { 27 | signed char slide1[256], slide2[256]; 28 | ge25519_pniels pre1[PRE1_SIZE], neg; 29 | ge25519_p3 d1; 30 | ge25519_p1p1 t; 31 | ge25519_niels nneg; 32 | fe25519 d; 33 | int i; 34 | 35 | sc25519_slide(slide1, s1, S1_SWINDOWSIZE); 36 | sc25519_slide(slide2, s2, S2_SWINDOWSIZE); 37 | 38 | /* precomputation */ 39 | pre1[0] = *(ge25519_pniels *)p1; 40 | ge25519_dbl_p1p1(&t,(ge25519_p2 *)pre1); ge25519_p1p1_to_p3(&d1, &t); 41 | /* Convert pre[0] to projective Niels representation */ 42 | d = pre1[0].ysubx; 43 | fe25519_sub(&pre1[0].ysubx, &pre1[0].xaddy, &pre1[0].ysubx); 44 | fe25519_add(&pre1[0].xaddy, &pre1[0].xaddy, &d); 45 | fe25519_mul(&pre1[0].t2d, &pre1[0].t2d, &ec2d); 46 | 47 | for(i=0;i= 0;--i) { 59 | if (slide1[i] || slide2[i]) goto firstbit; 60 | } 61 | 62 | for(;i>=0;i--) 63 | { 64 | firstbit: 65 | 66 | ge25519_dbl_p1p1(&t, (ge25519_p2 *)r); 67 | 68 | if(slide1[i]>0) 69 | { 70 | ge25519_p1p1_to_p3(r, &t); 71 | ge25519_pnielsadd_p1p1(&t, r, &pre1[slide1[i]/2]); 72 | } 73 | else if(slide1[i]<0) 74 | { 75 | ge25519_p1p1_to_p3(r, &t); 76 | neg = pre1[-slide1[i]/2]; 77 | d = neg.ysubx; 78 | neg.ysubx = neg.xaddy; 79 | neg.xaddy = d; 80 | fe25519_neg(&neg.t2d, &neg.t2d); 81 | ge25519_pnielsadd_p1p1(&t, r, &neg); 82 | } 83 | 84 | if(slide2[i]>0) 85 | { 86 | ge25519_p1p1_to_p3(r, &t); 87 | ge25519_nielsadd_p1p1(&t, r, &pre2[slide2[i]/2]); 88 | } 89 | else if(slide2[i]<0) 90 | { 91 | ge25519_p1p1_to_p3(r, &t); 92 | nneg = pre2[-slide2[i]/2]; 93 | d = nneg.ysubx; 94 | nneg.ysubx = nneg.xaddy; 95 | nneg.xaddy = d; 96 | fe25519_neg(&nneg.t2d, &nneg.t2d); 97 | ge25519_nielsadd_p1p1(&t, r, &nneg); 98 | } 99 | 100 | ge25519_p1p1_to_p2((ge25519_p2 *)r, &t); 101 | } 102 | } 103 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-64-24k/ge25519_isneutral.c: -------------------------------------------------------------------------------- 1 | #include "fe25519.h" 2 | #include "ge25519.h" 3 | 4 | int ge25519_isneutral_vartime(const ge25519_p3 *p) 5 | { 6 | if(!fe25519_iszero_vartime(&p->x)) return 0; 7 | if(!fe25519_iseq_vartime(&p->y, &p->z)) return 0; 8 | return 1; 9 | } 10 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-64-24k/ge25519_multi_scalarmult.c: -------------------------------------------------------------------------------- 1 | #include "fe25519.h" 2 | #include "sc25519.h" 3 | #include "ge25519.h" 4 | #include "index_heap.h" 5 | 6 | static void setneutral(ge25519 *r) 7 | { 8 | fe25519_setint(&r->x,0); 9 | fe25519_setint(&r->y,1); 10 | fe25519_setint(&r->z,1); 11 | fe25519_setint(&r->t,0); 12 | } 13 | 14 | static void ge25519_scalarmult_vartime_2limbs(ge25519 *r, ge25519 *p, sc25519 *s) 15 | { 16 | if (s->v[1] == 0 && s->v[0] == 1) /* This will happen most of the time after Bos-Coster */ 17 | *r = *p; 18 | else if (s->v[1] == 0 && s->v[0] == 0) /* This won't ever happen, except for all scalars == 0 in Bos-Coster */ 19 | setneutral(r); 20 | else 21 | { 22 | ge25519 d; 23 | unsigned long long mask = (1ULL << 63); 24 | int i = 1; 25 | while(!(mask & s->v[1]) && mask != 0) 26 | mask >>= 1; 27 | if(mask == 0) 28 | { 29 | mask = (1ULL << 63); 30 | i = 0; 31 | while(!(mask & s->v[0]) && mask != 0) 32 | mask >>= 1; 33 | } 34 | d = *p; 35 | mask >>= 1; 36 | for(;mask != 0;mask >>= 1) 37 | { 38 | ge25519_double(&d,&d); 39 | if(s->v[i] & mask) 40 | ge25519_add(&d,&d,p); 41 | } 42 | if(i==1) 43 | { 44 | mask = (1ULL << 63); 45 | for(;mask != 0;mask >>= 1) 46 | { 47 | ge25519_double(&d,&d); 48 | if(s->v[0] & mask) 49 | ge25519_add(&d,&d,p); 50 | } 51 | } 52 | *r = d; 53 | } 54 | } 55 | 56 | /* caller's responsibility to ensure npoints >= 5 */ 57 | void ge25519_multi_scalarmult_vartime(ge25519_p3 *r, ge25519_p3 *p, sc25519 *s, const unsigned long long npoints) 58 | { 59 | unsigned long long pos[npoints]; 60 | unsigned long long hlen=((npoints+1)/2)|1; 61 | unsigned long long max1, max2,i; 62 | 63 | heap_init(pos, hlen, s); 64 | 65 | for(i=0;;i++) 66 | { 67 | heap_get2max(pos, &max1, &max2, s); 68 | if((s[max1].v[3] == 0) || (sc25519_iszero_vartime(&s[max2]))) break; 69 | sc25519_sub_nored(&s[max1],&s[max1],&s[max2]); 70 | ge25519_add(&p[max2],&p[max2],&p[max1]); 71 | heap_rootreplaced(pos, hlen, s); 72 | } 73 | for(;;i++) 74 | { 75 | heap_get2max(pos, &max1, &max2, s); 76 | if((s[max1].v[2] == 0) || (sc25519_iszero_vartime(&s[max2]))) break; 77 | sc25519_sub_nored(&s[max1],&s[max1],&s[max2]); 78 | ge25519_add(&p[max2],&p[max2],&p[max1]); 79 | heap_rootreplaced_3limbs(pos, hlen, s); 80 | } 81 | /* We know that (npoints-1)/2 scalars are only 128-bit scalars */ 82 | heap_extend(pos, hlen, npoints, s); 83 | hlen = npoints; 84 | for(;;i++) 85 | { 86 | heap_get2max(pos, &max1, &max2, s); 87 | if((s[max1].v[1] == 0) || (sc25519_iszero_vartime(&s[max2]))) break; 88 | sc25519_sub_nored(&s[max1],&s[max1],&s[max2]); 89 | ge25519_add(&p[max2],&p[max2],&p[max1]); 90 | heap_rootreplaced_2limbs(pos, hlen, s); 91 | } 92 | for(;;i++) 93 | { 94 | heap_get2max(pos, &max1, &max2, s); 95 | if(sc25519_iszero_vartime(&s[max2])) break; 96 | sc25519_sub_nored(&s[max1],&s[max1],&s[max2]); 97 | ge25519_add(&p[max2],&p[max2],&p[max1]); 98 | heap_rootreplaced_1limb(pos, hlen, s); 99 | } 100 | 101 | ge25519_scalarmult_vartime_2limbs(r, &p[max1], &s[max1]); 102 | } 103 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-64-24k/ge25519_pack.c: -------------------------------------------------------------------------------- 1 | #include "fe25519.h" 2 | #include "sc25519.h" 3 | #include "ge25519.h" 4 | 5 | void ge25519_pack(unsigned char r[32], const ge25519_p3 *p) 6 | { 7 | fe25519 tx, ty, zi; 8 | fe25519_invert(&zi, &p->z); 9 | fe25519_mul(&tx, &p->x, &zi); 10 | fe25519_mul(&ty, &p->y, &zi); 11 | fe25519_pack(r, &ty); 12 | r[31] ^= fe25519_getparity(&tx) << 7; 13 | } 14 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-64-24k/ge25519_scalarmult_base.c: -------------------------------------------------------------------------------- 1 | #include "fe25519.h" 2 | #include "sc25519.h" 3 | #include "ge25519.h" 4 | 5 | /* Multiples of the base point in Niels' representation */ 6 | static const ge25519_niels ge25519_base_multiples_niels[] = { 7 | #ifdef SMALLTABLES 8 | #include "ge25519_base_niels_smalltables.data" 9 | #else 10 | #include "ge25519_base_niels.data" 11 | #endif 12 | }; 13 | 14 | /* d */ 15 | static const fe25519 ecd = {{0x75EB4DCA135978A3, 0x00700A4D4141D8AB, 0x8CC740797779E898, 0x52036CEE2B6FFE73}}; 16 | 17 | void ge25519_scalarmult_base(ge25519_p3 *r, const sc25519 *s) 18 | { 19 | signed char b[64]; 20 | int i; 21 | ge25519_niels t; 22 | fe25519 d; 23 | 24 | sc25519_window4(b,s); 25 | 26 | #ifdef SMALLTABLES 27 | ge25519_p1p1 tp1p1; 28 | choose_t((ge25519_niels *)r, 0, (signed long long) b[1], ge25519_base_multiples_niels); 29 | fe25519_sub(&d, &r->y, &r->x); 30 | fe25519_add(&r->y, &r->y, &r->x); 31 | r->x = d; 32 | r->t = r->z; 33 | fe25519_setint(&r->z,2); 34 | for(i=3;i<64;i+=2) 35 | { 36 | choose_t(&t, (unsigned long long) i/2, (signed long long) b[i], ge25519_base_multiples_niels); 37 | ge25519_nielsadd2(r, &t); 38 | } 39 | ge25519_dbl_p1p1(&tp1p1,(ge25519_p2 *)r); 40 | ge25519_p1p1_to_p2((ge25519_p2 *)r, &tp1p1); 41 | ge25519_dbl_p1p1(&tp1p1,(ge25519_p2 *)r); 42 | ge25519_p1p1_to_p2((ge25519_p2 *)r, &tp1p1); 43 | ge25519_dbl_p1p1(&tp1p1,(ge25519_p2 *)r); 44 | ge25519_p1p1_to_p2((ge25519_p2 *)r, &tp1p1); 45 | ge25519_dbl_p1p1(&tp1p1,(ge25519_p2 *)r); 46 | ge25519_p1p1_to_p3(r, &tp1p1); 47 | choose_t(&t, (unsigned long long) 0, (signed long long) b[0], ge25519_base_multiples_niels); 48 | fe25519_mul(&t.t2d, &t.t2d, &ecd); 49 | ge25519_nielsadd2(r, &t); 50 | for(i=2;i<64;i+=2) 51 | { 52 | choose_t(&t, (unsigned long long) i/2, (signed long long) b[i], ge25519_base_multiples_niels); 53 | ge25519_nielsadd2(r, &t); 54 | } 55 | #else 56 | choose_t((ge25519_niels *)r, 0, (signed long long) b[0], ge25519_base_multiples_niels); 57 | fe25519_sub(&d, &r->y, &r->x); 58 | fe25519_add(&r->y, &r->y, &r->x); 59 | r->x = d; 60 | r->t = r->z; 61 | fe25519_setint(&r->z,2); 62 | for(i=1;i<64;i++) 63 | { 64 | choose_t(&t, (unsigned long long) i, (signed long long) b[i], ge25519_base_multiples_niels); 65 | ge25519_nielsadd2(r, &t); 66 | } 67 | #endif 68 | } 69 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-64-24k/ge25519_unpackneg.c: -------------------------------------------------------------------------------- 1 | #include "fe25519.h" 2 | #include "ge25519.h" 3 | 4 | /* d */ 5 | static const fe25519 ecd = {{0x75EB4DCA135978A3, 0x00700A4D4141D8AB, 0x8CC740797779E898, 0x52036CEE2B6FFE73}}; 6 | /* sqrt(-1) */ 7 | static const fe25519 sqrtm1 = {{0xC4EE1B274A0EA0B0, 0x2F431806AD2FE478, 0x2B4D00993DFBD7A7, 0x2B8324804FC1DF0B}}; 8 | 9 | /* return 0 on success, -1 otherwise */ 10 | int ge25519_unpackneg_vartime(ge25519_p3 *r, const unsigned char p[32]) 11 | { 12 | fe25519 t, chk, num, den, den2, den4, den6; 13 | unsigned char par = p[31] >> 7; 14 | 15 | fe25519_setint(&r->z,1); 16 | fe25519_unpack(&r->y, p); 17 | fe25519_square(&num, &r->y); /* x = y^2 */ 18 | fe25519_mul(&den, &num, &ecd); /* den = dy^2 */ 19 | fe25519_sub(&num, &num, &r->z); /* x = y^2-1 */ 20 | fe25519_add(&den, &r->z, &den); /* den = dy^2+1 */ 21 | 22 | /* Computation of sqrt(num/den) 23 | 1.: computation of num^((p-5)/8)*den^((7p-35)/8) = (num*den^7)^((p-5)/8) 24 | */ 25 | fe25519_square(&den2, &den); 26 | fe25519_square(&den4, &den2); 27 | fe25519_mul(&den6, &den4, &den2); 28 | fe25519_mul(&t, &den6, &num); 29 | fe25519_mul(&t, &t, &den); 30 | 31 | fe25519_pow2523(&t, &t); 32 | /* 2. computation of r->x = t * num * den^3 33 | */ 34 | fe25519_mul(&t, &t, &num); 35 | fe25519_mul(&t, &t, &den); 36 | fe25519_mul(&t, &t, &den); 37 | fe25519_mul(&r->x, &t, &den); 38 | 39 | /* 3. Check whether sqrt computation gave correct result, multiply by sqrt(-1) if not: 40 | */ 41 | fe25519_square(&chk, &r->x); 42 | fe25519_mul(&chk, &chk, &den); 43 | if (!fe25519_iseq_vartime(&chk, &num)) 44 | fe25519_mul(&r->x, &r->x, &sqrtm1); 45 | 46 | /* 4. Now we have one of the two square roots, except if input was not a square 47 | */ 48 | fe25519_square(&chk, &r->x); 49 | fe25519_mul(&chk, &chk, &den); 50 | if (!fe25519_iseq_vartime(&chk, &num)) 51 | return -1; 52 | 53 | /* 5. Choose the desired square root according to parity: 54 | */ 55 | if(fe25519_getparity(&r->x) != (1-par)) 56 | fe25519_neg(&r->x, &r->x); 57 | 58 | fe25519_mul(&r->t, &r->x, &r->y); 59 | return 0; 60 | } 61 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-64-24k/hram.c: -------------------------------------------------------------------------------- 1 | #include "crypto_hash_sha512.h" 2 | #include "hram.h" 3 | 4 | void get_hram(unsigned char *hram, const unsigned char *sm, const unsigned char *pk, unsigned char *playground, unsigned long long smlen) 5 | { 6 | unsigned long long i; 7 | 8 | for (i = 0;i < 32;++i) playground[i] = sm[i]; 9 | for (i = 32;i < 64;++i) playground[i] = pk[i-32]; 10 | for (i = 64;i < smlen;++i) playground[i] = sm[i]; 11 | 12 | crypto_hash_sha512(hram,playground,smlen); 13 | } 14 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-64-24k/hram.h: -------------------------------------------------------------------------------- 1 | #ifndef HRAM_H 2 | #define HRAM_H 3 | 4 | #define get_hram crypto_sign_ed25519_amd64_64_get_hram 5 | 6 | extern void get_hram(unsigned char *hram, const unsigned char *sm, const unsigned char *pk, unsigned char *playground, unsigned long long smlen); 7 | 8 | #endif 9 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-64-24k/implementors: -------------------------------------------------------------------------------- 1 | Daniel J. Bernstein 2 | Niels Duif 3 | Tanja Lange 4 | lead: Peter Schwabe 5 | Bo-Yin Yang 6 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-64-24k/index_heap.c: -------------------------------------------------------------------------------- 1 | #include "sc25519.h" 2 | #include "index_heap.h" 3 | 4 | /* caller's responsibility to ensure hlen>=3 */ 5 | void heap_init(unsigned long long *h, unsigned long long hlen, sc25519 *scalars) 6 | { 7 | h[0] = 0; 8 | unsigned long long i=1; 9 | while(i 0) 30 | { 31 | /* if(sc25519_lt_vartime(&scalars[h[ppos]], &scalars[h[pos]])) */ 32 | if(sc25519_lt(&scalars[h[ppos]], &scalars[h[pos]])) 33 | { 34 | t = h[ppos]; 35 | h[ppos] = h[pos]; 36 | h[pos] = t; 37 | pos = ppos; 38 | ppos = (pos-1)/2; 39 | } 40 | else break; 41 | } 42 | (*hlen)++; 43 | } 44 | 45 | /* Put the largest value in the heap in max1, the second largest in max2 */ 46 | void heap_get2max(unsigned long long *h, unsigned long long *max1, unsigned long long *max2, sc25519 *scalars) 47 | { 48 | *max1 = h[0]; 49 | *max2 = h[1]; 50 | if(sc25519_lt(&scalars[h[1]],&scalars[h[2]])) 51 | *max2 = h[2]; 52 | } 53 | 54 | /* After the root has been replaced, restore heap property */ 55 | /* extern void heap_rootreplaced(unsigned long long *h, unsigned long long hlen, sc25519 *scalars); 56 | */ 57 | /* extern void heap_rootreplaced_shortscalars(unsigned long long *h, unsigned long long hlen, sc25519 *scalars); 58 | */ 59 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-64-24k/index_heap.h: -------------------------------------------------------------------------------- 1 | #ifndef INDEX_HEAP_H 2 | #define INDEX_HEAP_H 3 | 4 | #include "sc25519.h" 5 | 6 | #define heap_init crypto_sign_ed25519_amd64_64_heap_init 7 | #define heap_extend crypto_sign_ed25519_amd64_64_heap_extend 8 | #define heap_pop crypto_sign_ed25519_amd64_64_heap_pop 9 | #define heap_push crypto_sign_ed25519_amd64_64_heap_push 10 | #define heap_get2max crypto_sign_ed25519_amd64_64_heap_get2max 11 | #define heap_rootreplaced crypto_sign_ed25519_amd64_64_heap_rootreplaced 12 | #define heap_rootreplaced_3limbs crypto_sign_ed25519_amd64_64_heap_rootreplaced_3limbs 13 | #define heap_rootreplaced_2limbs crypto_sign_ed25519_amd64_64_heap_rootreplaced_2limbs 14 | #define heap_rootreplaced_1limb crypto_sign_ed25519_amd64_64_heap_rootreplaced_1limb 15 | 16 | void heap_init(unsigned long long *h, unsigned long long hlen, sc25519 *scalars); 17 | 18 | void heap_extend(unsigned long long *h, unsigned long long oldlen, unsigned long long newlen, sc25519 *scalars); 19 | 20 | unsigned long long heap_pop(unsigned long long *h, unsigned long long *hlen, sc25519 *scalars); 21 | 22 | void heap_push(unsigned long long *h, unsigned long long *hlen, unsigned long long elem, sc25519 *scalars); 23 | 24 | void heap_get2max(unsigned long long *h, unsigned long long *max1, unsigned long long *max2, sc25519 *scalars); 25 | 26 | void heap_rootreplaced(unsigned long long *h, unsigned long long hlen, sc25519 *scalars); 27 | void heap_rootreplaced_3limbs(unsigned long long *h, unsigned long long hlen, sc25519 *scalars); 28 | void heap_rootreplaced_2limbs(unsigned long long *h, unsigned long long hlen, sc25519 *scalars); 29 | void heap_rootreplaced_1limb(unsigned long long *h, unsigned long long hlen, sc25519 *scalars); 30 | 31 | #endif 32 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-64-24k/keypair.c: -------------------------------------------------------------------------------- 1 | #include 2 | #include "crypto_sign.h" 3 | #include "crypto_hash_sha512.h" 4 | #include "randombytes.h" 5 | #include "ge25519.h" 6 | 7 | int crypto_sign_keypair(unsigned char *pk,unsigned char *sk) 8 | { 9 | unsigned char az[64]; 10 | sc25519 scsk; 11 | ge25519 gepk; 12 | 13 | randombytes(sk,32); 14 | crypto_hash_sha512(az,sk,32); 15 | az[0] &= 248; 16 | az[31] &= 127; 17 | az[31] |= 64; 18 | 19 | sc25519_from32bytes(&scsk,az); 20 | 21 | ge25519_scalarmult_base(&gepk, &scsk); 22 | ge25519_pack(pk, &gepk); 23 | memmove(sk + 32,pk,32); 24 | return 0; 25 | } 26 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-64-24k/open.c: -------------------------------------------------------------------------------- 1 | #include 2 | #include "crypto_sign.h" 3 | #include "crypto_verify_32.h" 4 | #include "crypto_hash_sha512.h" 5 | #include "ge25519.h" 6 | 7 | int crypto_sign_open( 8 | unsigned char *m,unsigned long long *mlen, 9 | const unsigned char *sm,unsigned long long smlen, 10 | const unsigned char *pk 11 | ) 12 | { 13 | unsigned char pkcopy[32]; 14 | unsigned char rcopy[32]; 15 | unsigned char hram[64]; 16 | unsigned char rcheck[32]; 17 | ge25519 get1, get2; 18 | sc25519 schram, scs; 19 | 20 | if (smlen < 64) goto badsig; 21 | if (sm[63] & 224) goto badsig; 22 | if (ge25519_unpackneg_vartime(&get1,pk)) goto badsig; 23 | 24 | memmove(pkcopy,pk,32); 25 | memmove(rcopy,sm,32); 26 | 27 | sc25519_from32bytes(&scs, sm+32); 28 | 29 | memmove(m,sm,smlen); 30 | memmove(m + 32,pkcopy,32); 31 | crypto_hash_sha512(hram,m,smlen); 32 | 33 | sc25519_from64bytes(&schram, hram); 34 | 35 | ge25519_double_scalarmult_vartime(&get2, &get1, &schram, &scs); 36 | ge25519_pack(rcheck, &get2); 37 | 38 | if (crypto_verify_32(rcopy,rcheck) == 0) { 39 | memmove(m,m + 64,smlen - 64); 40 | memset(m + smlen - 64,0,64); 41 | *mlen = smlen - 64; 42 | return 0; 43 | } 44 | 45 | badsig: 46 | *mlen = (unsigned long long) -1; 47 | memset(m,0,smlen); 48 | return -1; 49 | } 50 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-64-24k/sc25519.h: -------------------------------------------------------------------------------- 1 | #ifndef SC25519_H 2 | #define SC25519_H 3 | 4 | #define sc25519 crypto_sign_ed25519_amd64_64_sc25519 5 | #define shortsc25519 crypto_sign_ed25519_amd64_64_shortsc25519 6 | #define sc25519_from32bytes crypto_sign_ed25519_amd64_64_sc25519_from32bytes 7 | #define shortsc25519_from16bytes crypto_sign_ed25519_amd64_64_shortsc25519_from16bytes 8 | #define sc25519_from64bytes crypto_sign_ed25519_amd64_64_sc25519_from64bytes 9 | #define sc25519_from_shortsc crypto_sign_ed25519_amd64_64_sc25519_from_shortsc 10 | #define sc25519_to32bytes crypto_sign_ed25519_amd64_64_sc25519_to32bytes 11 | #define sc25519_iszero_vartime crypto_sign_ed25519_amd64_64_sc25519_iszero_vartime 12 | #define sc25519_isshort_vartime crypto_sign_ed25519_amd64_64_sc25519_isshort_vartime 13 | #define sc25519_lt crypto_sign_ed25519_amd64_64_sc25519_lt 14 | #define sc25519_add crypto_sign_ed25519_amd64_64_sc25519_add 15 | #define sc25519_sub_nored crypto_sign_ed25519_amd64_64_sc25519_sub_nored 16 | #define sc25519_mul crypto_sign_ed25519_amd64_64_sc25519_mul 17 | #define sc25519_mul_shortsc crypto_sign_ed25519_amd64_64_sc25519_mul_shortsc 18 | #define sc25519_window4 crypto_sign_ed25519_amd64_64_sc25519_window4 19 | #define sc25519_slide crypto_sign_ed25519_amd64_64_sc25519_slide 20 | #define sc25519_2interleave2 crypto_sign_ed25519_amd64_64_sc25519_2interleave2 21 | #define sc25519_barrett crypto_sign_ed25519_amd64_64_sc25519_barrett 22 | 23 | typedef struct 24 | { 25 | unsigned long long v[4]; 26 | } 27 | sc25519; 28 | 29 | typedef struct 30 | { 31 | unsigned long long v[2]; 32 | } 33 | shortsc25519; 34 | 35 | void sc25519_from32bytes(sc25519 *r, const unsigned char x[32]); 36 | 37 | void sc25519_from64bytes(sc25519 *r, const unsigned char x[64]); 38 | 39 | void sc25519_from_shortsc(sc25519 *r, const shortsc25519 *x); 40 | 41 | void sc25519_to32bytes(unsigned char r[32], const sc25519 *x); 42 | 43 | int sc25519_iszero_vartime(const sc25519 *x); 44 | 45 | int sc25519_lt(const sc25519 *x, const sc25519 *y); 46 | 47 | void sc25519_add(sc25519 *r, const sc25519 *x, const sc25519 *y); 48 | 49 | void sc25519_sub_nored(sc25519 *r, const sc25519 *x, const sc25519 *y); 50 | 51 | void sc25519_mul(sc25519 *r, const sc25519 *x, const sc25519 *y); 52 | 53 | void sc25519_mul_shortsc(sc25519 *r, const sc25519 *x, const shortsc25519 *y); 54 | 55 | /* Convert s into a representation of the form \sum_{i=0}^{63}r[i]2^(4*i) 56 | * with r[i] in {-8,...,7} 57 | */ 58 | void sc25519_window4(signed char r[85], const sc25519 *s); 59 | 60 | void sc25519_slide(signed char r[256], const sc25519 *s, int swindowsize); 61 | 62 | void sc25519_2interleave2(unsigned char r[127], const sc25519 *s1, const sc25519 *s2); 63 | 64 | void sc25519_barrett(sc25519 *r, unsigned long long x[8]); 65 | 66 | #endif 67 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-64-24k/sc25519_from32bytes.c: -------------------------------------------------------------------------------- 1 | #include "sc25519.h" 2 | 3 | /*Arithmetic modulo the group order n = 2^252 + 27742317777372353535851937790883648493 4 | * = 7237005577332262213973186563042994240857116359379907606001950938285454250989 5 | */ 6 | 7 | /* Contains order, 2*order, 4*order, 8*order, each represented in 4 consecutive unsigned long long */ 8 | static const unsigned long long order[16] = {0x5812631A5CF5D3EDULL, 0x14DEF9DEA2F79CD6ULL, 9 | 0x0000000000000000ULL, 0x1000000000000000ULL, 10 | 0xB024C634B9EBA7DAULL, 0x29BDF3BD45EF39ACULL, 11 | 0x0000000000000000ULL, 0x2000000000000000ULL, 12 | 0x60498C6973D74FB4ULL, 0x537BE77A8BDE7359ULL, 13 | 0x0000000000000000ULL, 0x4000000000000000ULL, 14 | 0xC09318D2E7AE9F68ULL, 0xA6F7CEF517BCE6B2ULL, 15 | 0x0000000000000000ULL, 0x8000000000000000ULL}; 16 | 17 | static unsigned long long smaller(unsigned long long a,unsigned long long b) 18 | { 19 | unsigned long long atop = a >> 32; 20 | unsigned long long abot = a & 4294967295; 21 | unsigned long long btop = b >> 32; 22 | unsigned long long bbot = b & 4294967295; 23 | unsigned long long atopbelowbtop = (atop - btop) >> 63; 24 | unsigned long long atopeqbtop = ((atop ^ btop) - 1) >> 63; 25 | unsigned long long abotbelowbbot = (abot - bbot) >> 63; 26 | return atopbelowbtop | (atopeqbtop & abotbelowbbot); 27 | } 28 | 29 | void sc25519_from32bytes(sc25519 *r, const unsigned char x[32]) 30 | { 31 | unsigned long long t[4]; 32 | unsigned long long b; 33 | unsigned long long mask; 34 | int i, j; 35 | 36 | /* assuming little-endian */ 37 | r->v[0] = *(unsigned long long *)x; 38 | r->v[1] = *(((unsigned long long *)x)+1); 39 | r->v[2] = *(((unsigned long long *)x)+2); 40 | r->v[3] = *(((unsigned long long *)x)+3); 41 | 42 | for(j=3;j>=0;j--) 43 | { 44 | b=0; 45 | for(i=0;i<4;i++) 46 | { 47 | b += order[4*j+i]; /* no overflow for this particular order */ 48 | t[i] = r->v[i] - b; 49 | b = smaller(r->v[i],b); 50 | } 51 | mask = b - 1; 52 | for(i=0;i<4;i++) 53 | r->v[i] ^= mask & (r->v[i] ^ t[i]); 54 | } 55 | } 56 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-64-24k/sc25519_from64bytes.c: -------------------------------------------------------------------------------- 1 | #include "sc25519.h" 2 | 3 | void sc25519_from64bytes(sc25519 *r, const unsigned char x[64]) 4 | { 5 | /* assuming little-endian representation of unsigned long long */ 6 | sc25519_barrett(r, (unsigned long long *)x); 7 | } 8 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-64-24k/sc25519_from_shortsc.c: -------------------------------------------------------------------------------- 1 | #include "sc25519.h" 2 | 3 | void sc25519_from_shortsc(sc25519 *r, const shortsc25519 *x) 4 | { 5 | r->v[0] = x->v[0]; 6 | r->v[1] = x->v[1]; 7 | r->v[2] = 0; 8 | r->v[3] = 0; 9 | } 10 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-64-24k/sc25519_iszero.c: -------------------------------------------------------------------------------- 1 | #include "sc25519.h" 2 | 3 | int sc25519_iszero_vartime(const sc25519 *x) 4 | { 5 | if(x->v[0] != 0) return 0; 6 | if(x->v[1] != 0) return 0; 7 | if(x->v[2] != 0) return 0; 8 | if(x->v[3] != 0) return 0; 9 | return 1; 10 | } 11 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-64-24k/sc25519_lt.s: -------------------------------------------------------------------------------- 1 | 2 | # qhasm: int64 xp 3 | 4 | # qhasm: int64 yp 5 | 6 | # qhasm: int64 ret 7 | 8 | # qhasm: input xp 9 | 10 | # qhasm: input yp 11 | 12 | # qhasm: output ret 13 | 14 | # qhasm: int64 t0 15 | 16 | # qhasm: int64 t1 17 | 18 | # qhasm: int64 t2 19 | 20 | # qhasm: int64 t3 21 | 22 | # qhasm: int64 doof 23 | 24 | # qhasm: int64 caller1 25 | 26 | # qhasm: int64 caller2 27 | 28 | # qhasm: int64 caller3 29 | 30 | # qhasm: int64 caller4 31 | 32 | # qhasm: int64 caller5 33 | 34 | # qhasm: int64 caller6 35 | 36 | # qhasm: int64 caller7 37 | 38 | # qhasm: caller caller1 39 | 40 | # qhasm: caller caller2 41 | 42 | # qhasm: caller caller3 43 | 44 | # qhasm: caller caller4 45 | 46 | # qhasm: caller caller5 47 | 48 | # qhasm: caller caller6 49 | 50 | # qhasm: caller caller7 51 | 52 | # qhasm: stack64 caller4_stack 53 | 54 | # qhasm: stack64 caller5_stack 55 | 56 | # qhasm: stack64 caller6_stack 57 | 58 | # qhasm: stack64 caller7_stack 59 | 60 | # qhasm: enter crypto_sign_ed25519_amd64_64_sc25519_lt 61 | .text 62 | .p2align 5 63 | .globl _crypto_sign_ed25519_amd64_64_sc25519_lt 64 | .globl crypto_sign_ed25519_amd64_64_sc25519_lt 65 | _crypto_sign_ed25519_amd64_64_sc25519_lt: 66 | crypto_sign_ed25519_amd64_64_sc25519_lt: 67 | mov %rsp,%r11 68 | and $31,%r11 69 | add $0,%r11 70 | sub %r11,%rsp 71 | 72 | # qhasm: t0 = *(uint64 *)(xp + 0) 73 | # asm 1: movq 0(t0=int64#3 74 | # asm 2: movq 0(t0=%rdx 75 | movq 0(%rdi),%rdx 76 | 77 | # qhasm: t1 = *(uint64 *)(xp + 8) 78 | # asm 1: movq 8(t1=int64#4 79 | # asm 2: movq 8(t1=%rcx 80 | movq 8(%rdi),%rcx 81 | 82 | # qhasm: t2 = *(uint64 *)(xp + 16) 83 | # asm 1: movq 16(t2=int64#5 84 | # asm 2: movq 16(t2=%r8 85 | movq 16(%rdi),%r8 86 | 87 | # qhasm: t3 = *(uint64 *)(xp + 24) 88 | # asm 1: movq 24(t3=int64#1 89 | # asm 2: movq 24(t3=%rdi 90 | movq 24(%rdi),%rdi 91 | 92 | # qhasm: carry? t0 -= *(uint64 *)(yp + 0) 93 | # asm 1: subq 0(ret=int64#1 114 | # asm 2: mov $0,>ret=%rdi 115 | mov $0,%rdi 116 | 117 | # qhasm: doof = 1 118 | # asm 1: mov $1,>doof=int64#2 119 | # asm 2: mov $1,>doof=%rsi 120 | mov $1,%rsi 121 | 122 | # qhasm: ret = doof if carry 123 | # asm 1: cmovc v, y->v); 11 | sc25519_barrett(r, t); 12 | } 13 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-64-24k/sc25519_mul_shortsc.c: -------------------------------------------------------------------------------- 1 | #include "sc25519.h" 2 | 3 | void sc25519_mul_shortsc(sc25519 *r, const sc25519 *x, const shortsc25519 *y) 4 | { 5 | /* XXX: This wants to be faster */ 6 | sc25519 t; 7 | sc25519_from_shortsc(&t, y); 8 | sc25519_mul(r, x, &t); 9 | } 10 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-64-24k/sc25519_slide.c: -------------------------------------------------------------------------------- 1 | #include "sc25519.h" 2 | 3 | void sc25519_slide(signed char r[256], const sc25519 *s, int swindowsize) 4 | { 5 | int i,j,k,b,m=(1<<(swindowsize-1))-1, soplen=256; 6 | unsigned long long sv0 = s->v[0]; 7 | unsigned long long sv1 = s->v[1]; 8 | unsigned long long sv2 = s->v[2]; 9 | unsigned long long sv3 = s->v[3]; 10 | 11 | /* first put the binary expansion into r */ 12 | for(i=0;i<64;i++) { 13 | r[i] = sv0 & 1; 14 | r[i+64] = sv1 & 1; 15 | r[i+128] = sv2 & 1; 16 | r[i+192] = sv3 & 1; 17 | sv0 >>= 1; 18 | sv1 >>= 1; 19 | sv2 >>= 1; 20 | sv3 >>= 1; 21 | } 22 | 23 | /* Making it sliding window */ 24 | for (j = 0;j < soplen;++j) 25 | { 26 | if (r[j]) { 27 | for (b = 1;b < soplen - j && b <= 6;++b) { 28 | if (r[j] + (r[j + b] << b) <= m) 29 | { 30 | r[j] += r[j + b] << b; r[j + b] = 0; 31 | } 32 | else if (r[j] - (r[j + b] << b) >= -m) 33 | { 34 | r[j] -= r[j + b] << b; 35 | for (k = j + b;k < soplen;++k) 36 | { 37 | if (!r[k]) { 38 | r[k] = 1; 39 | break; 40 | } 41 | r[k] = 0; 42 | } 43 | } 44 | else if (r[j + b]) 45 | break; 46 | } 47 | } 48 | } 49 | } 50 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-64-24k/sc25519_to32bytes.c: -------------------------------------------------------------------------------- 1 | #include "sc25519.h" 2 | 3 | void sc25519_to32bytes(unsigned char r[32], const sc25519 *x) 4 | { 5 | /* assuming little-endian */ 6 | int i; 7 | for(i=0;i<32;i++) r[i] = i[(unsigned char *)x->v]; 8 | } 9 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-64-24k/sc25519_window4.c: -------------------------------------------------------------------------------- 1 | #include "sc25519.h" 2 | 3 | void sc25519_window4(signed char r[64], const sc25519 *s) 4 | { 5 | char carry; 6 | int i; 7 | for(i=0;i<16;i++) 8 | r[i] = (s->v[0] >> (4*i)) & 15; 9 | for(i=0;i<16;i++) 10 | r[i+16] = (s->v[1] >> (4*i)) & 15; 11 | for(i=0;i<16;i++) 12 | r[i+32] = (s->v[2] >> (4*i)) & 15; 13 | for(i=0;i<16;i++) 14 | r[i+48] = (s->v[3] >> (4*i)) & 15; 15 | 16 | /* Making it signed */ 17 | carry = 0; 18 | for(i=0;i<63;i++) 19 | { 20 | r[i] += carry; 21 | r[i+1] += r[i] >> 4; 22 | r[i] &= 15; 23 | carry = r[i] >> 3; 24 | r[i] -= carry << 4; 25 | } 26 | r[63] += carry; 27 | } 28 | -------------------------------------------------------------------------------- /ed25519-supercop/amd64-64-24k/sign.c: -------------------------------------------------------------------------------- 1 | #include 2 | #include "crypto_sign.h" 3 | #include "crypto_hash_sha512.h" 4 | #include "ge25519.h" 5 | 6 | int crypto_sign( 7 | unsigned char *sm,unsigned long long *smlen, 8 | const unsigned char *m,unsigned long long mlen, 9 | const unsigned char *sk 10 | ) 11 | { 12 | unsigned char pk[32]; 13 | unsigned char az[64]; 14 | unsigned char nonce[64]; 15 | unsigned char hram[64]; 16 | sc25519 sck, scs, scsk; 17 | ge25519 ger; 18 | 19 | memmove(pk,sk + 32,32); 20 | /* pk: 32-byte public key A */ 21 | 22 | crypto_hash_sha512(az,sk,32); 23 | az[0] &= 248; 24 | az[31] &= 127; 25 | az[31] |= 64; 26 | /* az: 32-byte scalar a, 32-byte randomizer z */ 27 | 28 | *smlen = mlen + 64; 29 | memmove(sm + 64,m,mlen); 30 | memmove(sm + 32,az + 32,32); 31 | /* sm: 32-byte uninit, 32-byte z, mlen-byte m */ 32 | 33 | crypto_hash_sha512(nonce, sm+32, mlen+32); 34 | /* nonce: 64-byte H(z,m) */ 35 | 36 | sc25519_from64bytes(&sck, nonce); 37 | ge25519_scalarmult_base(&ger, &sck); 38 | ge25519_pack(sm, &ger); 39 | /* sm: 32-byte R, 32-byte z, mlen-byte m */ 40 | 41 | memmove(sm + 32,pk,32); 42 | /* sm: 32-byte R, 32-byte A, mlen-byte m */ 43 | 44 | crypto_hash_sha512(hram,sm,mlen + 64); 45 | /* hram: 64-byte H(R,A,m) */ 46 | 47 | sc25519_from64bytes(&scs, hram); 48 | sc25519_from32bytes(&scsk, az); 49 | sc25519_mul(&scs, &scs, &scsk); 50 | sc25519_add(&scs, &scs, &sck); 51 | /* scs: S = nonce + H(R,A,m)a */ 52 | 53 | sc25519_to32bytes(sm + 32,&scs); 54 | /* sm: 32-byte R, 32-byte S, mlen-byte m */ 55 | 56 | return 0; 57 | } 58 | -------------------------------------------------------------------------------- /ed25519-supercop/checksumbig: -------------------------------------------------------------------------------- 1 | 6dacbe42d112348ae7abf32ff69ac95041f2e6cd9fe91eeab9ca10dedf318812 2 | -------------------------------------------------------------------------------- /ed25519-supercop/checksumsmall: -------------------------------------------------------------------------------- 1 | 6d6cae511aa24af47411243ba5bc2a84f8e827dfe80aca92ec3769061471952a 2 | -------------------------------------------------------------------------------- /ed25519-supercop/description: -------------------------------------------------------------------------------- 1 | EdDSA signatures using Curve25519 2 | -------------------------------------------------------------------------------- /ed25519-supercop/designers: -------------------------------------------------------------------------------- 1 | Daniel J. Bernstein 2 | Niels Duif 3 | Tanja Lange 4 | Peter Schwabe 5 | Bo-Yin Yang 6 | -------------------------------------------------------------------------------- /ed25519-supercop/ref/api.h: -------------------------------------------------------------------------------- 1 | #define CRYPTO_SECRETKEYBYTES 64 2 | #define CRYPTO_PUBLICKEYBYTES 32 3 | #define CRYPTO_BYTES 64 4 | #define CRYPTO_DETERMINISTIC 1 5 | -------------------------------------------------------------------------------- /ed25519-supercop/ref/fe25519.h: -------------------------------------------------------------------------------- 1 | #ifndef FE25519_H 2 | #define FE25519_H 3 | 4 | #include "crypto_int32.h" 5 | #include "crypto_uint32.h" 6 | 7 | #define fe25519 crypto_sign_ed25519_ref_fe25519 8 | #define fe25519_freeze crypto_sign_ed25519_ref_fe25519_freeze 9 | #define fe25519_unpack crypto_sign_ed25519_ref_fe25519_unpack 10 | #define fe25519_pack crypto_sign_ed25519_ref_fe25519_pack 11 | #define fe25519_iszero crypto_sign_ed25519_ref_fe25519_iszero 12 | #define fe25519_iseq_vartime crypto_sign_ed25519_ref_fe25519_iseq_vartime 13 | #define fe25519_cmov crypto_sign_ed25519_ref_fe25519_cmov 14 | #define fe25519_setone crypto_sign_ed25519_ref_fe25519_setone 15 | #define fe25519_setzero crypto_sign_ed25519_ref_fe25519_setzero 16 | #define fe25519_neg crypto_sign_ed25519_ref_fe25519_neg 17 | #define fe25519_getparity crypto_sign_ed25519_ref_fe25519_getparity 18 | #define fe25519_add crypto_sign_ed25519_ref_fe25519_add 19 | #define fe25519_sub crypto_sign_ed25519_ref_fe25519_sub 20 | #define fe25519_mul crypto_sign_ed25519_ref_fe25519_mul 21 | #define fe25519_square crypto_sign_ed25519_ref_fe25519_square 22 | #define fe25519_invert crypto_sign_ed25519_ref_fe25519_invert 23 | #define fe25519_pow2523 crypto_sign_ed25519_ref_fe25519_pow2523 24 | 25 | typedef struct 26 | { 27 | crypto_uint32 v[32]; 28 | } 29 | fe25519; 30 | 31 | void fe25519_freeze(fe25519 *r); 32 | 33 | void fe25519_unpack(fe25519 *r, const unsigned char x[32]); 34 | 35 | void fe25519_pack(unsigned char r[32], const fe25519 *x); 36 | 37 | int fe25519_iszero(const fe25519 *x); 38 | 39 | int fe25519_iseq_vartime(const fe25519 *x, const fe25519 *y); 40 | 41 | void fe25519_cmov(fe25519 *r, const fe25519 *x, unsigned char b); 42 | 43 | void fe25519_setone(fe25519 *r); 44 | 45 | void fe25519_setzero(fe25519 *r); 46 | 47 | void fe25519_neg(fe25519 *r, const fe25519 *x); 48 | 49 | unsigned char fe25519_getparity(const fe25519 *x); 50 | 51 | void fe25519_add(fe25519 *r, const fe25519 *x, const fe25519 *y); 52 | 53 | void fe25519_sub(fe25519 *r, const fe25519 *x, const fe25519 *y); 54 | 55 | void fe25519_mul(fe25519 *r, const fe25519 *x, const fe25519 *y); 56 | 57 | void fe25519_square(fe25519 *r, const fe25519 *x); 58 | 59 | void fe25519_invert(fe25519 *r, const fe25519 *x); 60 | 61 | void fe25519_pow2523(fe25519 *r, const fe25519 *x); 62 | 63 | #endif 64 | -------------------------------------------------------------------------------- /ed25519-supercop/ref/ge25519.h: -------------------------------------------------------------------------------- 1 | #ifndef GE25519_H 2 | #define GE25519_H 3 | 4 | #include "fe25519.h" 5 | #include "sc25519.h" 6 | 7 | #define ge25519 crypto_sign_ed25519_ref_ge25519 8 | #define ge25519_base crypto_sign_ed25519_ref_ge25519_base 9 | #define ge25519_unpackneg_vartime crypto_sign_ed25519_ref_unpackneg_vartime 10 | #define ge25519_pack crypto_sign_ed25519_ref_pack 11 | #define ge25519_isneutral_vartime crypto_sign_ed25519_ref_isneutral_vartime 12 | #define ge25519_double_scalarmult_vartime crypto_sign_ed25519_ref_double_scalarmult_vartime 13 | #define ge25519_scalarmult_base crypto_sign_ed25519_ref_scalarmult_base 14 | 15 | typedef struct 16 | { 17 | fe25519 x; 18 | fe25519 y; 19 | fe25519 z; 20 | fe25519 t; 21 | } ge25519; 22 | 23 | const ge25519 ge25519_base; 24 | 25 | int ge25519_unpackneg_vartime(ge25519 *r, const unsigned char p[32]); 26 | 27 | void ge25519_pack(unsigned char r[32], const ge25519 *p); 28 | 29 | int ge25519_isneutral_vartime(const ge25519 *p); 30 | 31 | void ge25519_double_scalarmult_vartime(ge25519 *r, const ge25519 *p1, const sc25519 *s1, const ge25519 *p2, const sc25519 *s2); 32 | 33 | void ge25519_scalarmult_base(ge25519 *r, const sc25519 *s); 34 | 35 | #endif 36 | -------------------------------------------------------------------------------- /ed25519-supercop/ref/implementors: -------------------------------------------------------------------------------- 1 | Daniel J. Bernstein 2 | Niels Duif 3 | Tanja Lange 4 | lead: Peter Schwabe 5 | Bo-Yin Yang 6 | -------------------------------------------------------------------------------- /ed25519-supercop/ref/keypair.c: -------------------------------------------------------------------------------- 1 | #include 2 | #include "crypto_sign.h" 3 | #include "crypto_hash_sha512.h" 4 | #include "randombytes.h" 5 | #include "ge25519.h" 6 | 7 | int crypto_sign_keypair(unsigned char *pk,unsigned char *sk) 8 | { 9 | unsigned char az[64]; 10 | sc25519 scsk; 11 | ge25519 gepk; 12 | 13 | randombytes(sk,32); 14 | crypto_hash_sha512(az,sk,32); 15 | az[0] &= 248; 16 | az[31] &= 127; 17 | az[31] |= 64; 18 | 19 | sc25519_from32bytes(&scsk,az); 20 | 21 | ge25519_scalarmult_base(&gepk, &scsk); 22 | ge25519_pack(pk, &gepk); 23 | memmove(sk + 32,pk,32); 24 | return 0; 25 | } 26 | -------------------------------------------------------------------------------- /ed25519-supercop/ref/open.c: -------------------------------------------------------------------------------- 1 | #include 2 | #include "crypto_sign.h" 3 | #include "crypto_verify_32.h" 4 | #include "crypto_hash_sha512.h" 5 | #include "ge25519.h" 6 | 7 | int crypto_sign_open( 8 | unsigned char *m,unsigned long long *mlen, 9 | const unsigned char *sm,unsigned long long smlen, 10 | const unsigned char *pk 11 | ) 12 | { 13 | unsigned char pkcopy[32]; 14 | unsigned char rcopy[32]; 15 | unsigned char hram[64]; 16 | unsigned char rcheck[32]; 17 | ge25519 get1, get2; 18 | sc25519 schram, scs; 19 | 20 | if (smlen < 64) goto badsig; 21 | if (sm[63] & 224) goto badsig; 22 | if (ge25519_unpackneg_vartime(&get1,pk)) goto badsig; 23 | 24 | memmove(pkcopy,pk,32); 25 | memmove(rcopy,sm,32); 26 | 27 | sc25519_from32bytes(&scs, sm+32); 28 | 29 | memmove(m,sm,smlen); 30 | memmove(m + 32,pkcopy,32); 31 | crypto_hash_sha512(hram,m,smlen); 32 | 33 | sc25519_from64bytes(&schram, hram); 34 | 35 | ge25519_double_scalarmult_vartime(&get2, &get1, &schram, &ge25519_base, &scs); 36 | ge25519_pack(rcheck, &get2); 37 | 38 | if (crypto_verify_32(rcopy,rcheck) == 0) { 39 | memmove(m,m + 64,smlen - 64); 40 | memset(m + smlen - 64,0,64); 41 | *mlen = smlen - 64; 42 | return 0; 43 | } 44 | 45 | badsig: 46 | *mlen = (unsigned long long) -1; 47 | memset(m,0,smlen); 48 | return -1; 49 | } 50 | -------------------------------------------------------------------------------- /ed25519-supercop/ref/sc25519.h: -------------------------------------------------------------------------------- 1 | #ifndef SC25519_H 2 | #define SC25519_H 3 | 4 | #include "crypto_int32.h" 5 | #include "crypto_uint32.h" 6 | 7 | #define sc25519 crypto_sign_ed25519_ref_sc25519 8 | #define shortsc25519 crypto_sign_ed25519_ref_shortsc25519 9 | #define sc25519_from32bytes crypto_sign_ed25519_ref_sc25519_from32bytes 10 | #define shortsc25519_from16bytes crypto_sign_ed25519_ref_shortsc25519_from16bytes 11 | #define sc25519_from64bytes crypto_sign_ed25519_ref_sc25519_from64bytes 12 | #define sc25519_from_shortsc crypto_sign_ed25519_ref_sc25519_from_shortsc 13 | #define sc25519_to32bytes crypto_sign_ed25519_ref_sc25519_to32bytes 14 | #define sc25519_iszero_vartime crypto_sign_ed25519_ref_sc25519_iszero_vartime 15 | #define sc25519_isshort_vartime crypto_sign_ed25519_ref_sc25519_isshort_vartime 16 | #define sc25519_lt_vartime crypto_sign_ed25519_ref_sc25519_lt_vartime 17 | #define sc25519_add crypto_sign_ed25519_ref_sc25519_add 18 | #define sc25519_sub_nored crypto_sign_ed25519_ref_sc25519_sub_nored 19 | #define sc25519_mul crypto_sign_ed25519_ref_sc25519_mul 20 | #define sc25519_mul_shortsc crypto_sign_ed25519_ref_sc25519_mul_shortsc 21 | #define sc25519_window3 crypto_sign_ed25519_ref_sc25519_window3 22 | #define sc25519_window5 crypto_sign_ed25519_ref_sc25519_window5 23 | #define sc25519_2interleave2 crypto_sign_ed25519_ref_sc25519_2interleave2 24 | 25 | typedef struct 26 | { 27 | crypto_uint32 v[32]; 28 | } 29 | sc25519; 30 | 31 | typedef struct 32 | { 33 | crypto_uint32 v[16]; 34 | } 35 | shortsc25519; 36 | 37 | void sc25519_from32bytes(sc25519 *r, const unsigned char x[32]); 38 | 39 | void shortsc25519_from16bytes(shortsc25519 *r, const unsigned char x[16]); 40 | 41 | void sc25519_from64bytes(sc25519 *r, const unsigned char x[64]); 42 | 43 | void sc25519_from_shortsc(sc25519 *r, const shortsc25519 *x); 44 | 45 | void sc25519_to32bytes(unsigned char r[32], const sc25519 *x); 46 | 47 | int sc25519_iszero_vartime(const sc25519 *x); 48 | 49 | int sc25519_isshort_vartime(const sc25519 *x); 50 | 51 | int sc25519_lt_vartime(const sc25519 *x, const sc25519 *y); 52 | 53 | void sc25519_add(sc25519 *r, const sc25519 *x, const sc25519 *y); 54 | 55 | void sc25519_sub_nored(sc25519 *r, const sc25519 *x, const sc25519 *y); 56 | 57 | void sc25519_mul(sc25519 *r, const sc25519 *x, const sc25519 *y); 58 | 59 | void sc25519_mul_shortsc(sc25519 *r, const sc25519 *x, const shortsc25519 *y); 60 | 61 | /* Convert s into a representation of the form \sum_{i=0}^{84}r[i]2^3 62 | * with r[i] in {-4,...,3} 63 | */ 64 | void sc25519_window3(signed char r[85], const sc25519 *s); 65 | 66 | /* Convert s into a representation of the form \sum_{i=0}^{50}r[i]2^5 67 | * with r[i] in {-16,...,15} 68 | */ 69 | void sc25519_window5(signed char r[51], const sc25519 *s); 70 | 71 | void sc25519_2interleave2(unsigned char r[127], const sc25519 *s1, const sc25519 *s2); 72 | 73 | #endif 74 | -------------------------------------------------------------------------------- /ed25519-supercop/ref/sign.c: -------------------------------------------------------------------------------- 1 | #include 2 | #include "crypto_sign.h" 3 | #include "crypto_hash_sha512.h" 4 | #include "ge25519.h" 5 | 6 | int crypto_sign( 7 | unsigned char *sm,unsigned long long *smlen, 8 | const unsigned char *m,unsigned long long mlen, 9 | const unsigned char *sk 10 | ) 11 | { 12 | unsigned char pk[32]; 13 | unsigned char az[64]; 14 | unsigned char nonce[64]; 15 | unsigned char hram[64]; 16 | sc25519 sck, scs, scsk; 17 | ge25519 ger; 18 | 19 | memmove(pk,sk + 32,32); 20 | /* pk: 32-byte public key A */ 21 | 22 | crypto_hash_sha512(az,sk,32); 23 | az[0] &= 248; 24 | az[31] &= 127; 25 | az[31] |= 64; 26 | /* az: 32-byte scalar a, 32-byte randomizer z */ 27 | 28 | *smlen = mlen + 64; 29 | memmove(sm + 64,m,mlen); 30 | memmove(sm + 32,az + 32,32); 31 | /* sm: 32-byte uninit, 32-byte z, mlen-byte m */ 32 | 33 | crypto_hash_sha512(nonce, sm+32, mlen+32); 34 | /* nonce: 64-byte H(z,m) */ 35 | 36 | sc25519_from64bytes(&sck, nonce); 37 | ge25519_scalarmult_base(&ger, &sck); 38 | ge25519_pack(sm, &ger); 39 | /* sm: 32-byte R, 32-byte z, mlen-byte m */ 40 | 41 | memmove(sm + 32,pk,32); 42 | /* sm: 32-byte R, 32-byte A, mlen-byte m */ 43 | 44 | crypto_hash_sha512(hram,sm,mlen + 64); 45 | /* hram: 64-byte H(R,A,m) */ 46 | 47 | sc25519_from64bytes(&scs, hram); 48 | sc25519_from32bytes(&scsk, az); 49 | sc25519_mul(&scs, &scs, &scsk); 50 | sc25519_add(&scs, &scs, &sck); 51 | /* scs: S = nonce + H(R,A,m)a */ 52 | 53 | sc25519_to32bytes(sm + 32,&scs); 54 | /* sm: 32-byte R, 32-byte S, mlen-byte m */ 55 | 56 | return 0; 57 | } 58 | -------------------------------------------------------------------------------- /ed25519-supercop/ref10/Makefile: -------------------------------------------------------------------------------- 1 | all: d.h d2.h sqrtm1.h base.h base2.h \ 2 | ge_add.h ge_sub.h \ 3 | ge_madd.h ge_msub.h \ 4 | ge_p2_dbl.h \ 5 | pow225521.h pow22523.h 6 | 7 | d.h: d.py 8 | python d.py > d.h 9 | 10 | d2.h: d2.py 11 | python d2.py > d2.h 12 | 13 | sqrtm1.h: sqrtm1.py 14 | python sqrtm1.py > sqrtm1.h 15 | 16 | base.h: base.py 17 | python base.py > base.h 18 | 19 | base2.h: base2.py 20 | python base2.py > base2.h 21 | 22 | ge_add.h: ge_add.q q2h.sh 23 | ./q2h.sh < ge_add.q > ge_add.h 24 | 25 | ge_sub.h: ge_sub.q q2h.sh 26 | ./q2h.sh < ge_sub.q > ge_sub.h 27 | 28 | ge_madd.h: ge_madd.q q2h.sh 29 | ./q2h.sh < ge_madd.q > ge_madd.h 30 | 31 | ge_msub.h: ge_msub.q q2h.sh 32 | ./q2h.sh < ge_msub.q > ge_msub.h 33 | 34 | ge_p2_dbl.h: ge_p2_dbl.q q2h.sh 35 | ./q2h.sh < ge_p2_dbl.q > ge_p2_dbl.h 36 | 37 | pow22523.h: pow22523.q q2h.sh 38 | ./q2h.sh < pow22523.q > pow22523.h 39 | 40 | pow225521.h: pow225521.q q2h.sh 41 | ./q2h.sh < pow225521.q > pow225521.h 42 | -------------------------------------------------------------------------------- /ed25519-supercop/ref10/README: -------------------------------------------------------------------------------- 1 | Public domain. 2 | -------------------------------------------------------------------------------- /ed25519-supercop/ref10/api.h: -------------------------------------------------------------------------------- 1 | #define CRYPTO_SECRETKEYBYTES 64 2 | #define CRYPTO_PUBLICKEYBYTES 32 3 | #define CRYPTO_BYTES 64 4 | #define CRYPTO_DETERMINISTIC 1 5 | -------------------------------------------------------------------------------- /ed25519-supercop/ref10/base.py: -------------------------------------------------------------------------------- 1 | b = 256 2 | q = 2**255 - 19 3 | l = 2**252 + 27742317777372353535851937790883648493 4 | 5 | def expmod(b,e,m): 6 | if e == 0: return 1 7 | t = expmod(b,e/2,m)**2 % m 8 | if e & 1: t = (t*b) % m 9 | return t 10 | 11 | def inv(x): 12 | return expmod(x,q-2,q) 13 | 14 | d = -121665 * inv(121666) 15 | I = expmod(2,(q-1)/4,q) 16 | 17 | def xrecover(y): 18 | xx = (y*y-1) * inv(d*y*y+1) 19 | x = expmod(xx,(q+3)/8,q) 20 | if (x*x - xx) % q != 0: x = (x*I) % q 21 | if x % 2 != 0: x = q-x 22 | return x 23 | 24 | By = 4 * inv(5) 25 | Bx = xrecover(By) 26 | B = [Bx % q,By % q] 27 | 28 | def edwards(P,Q): 29 | x1 = P[0] 30 | y1 = P[1] 31 | x2 = Q[0] 32 | y2 = Q[1] 33 | x3 = (x1*y2+x2*y1) * inv(1+d*x1*x2*y1*y2) 34 | y3 = (y1*y2+x1*x2) * inv(1-d*x1*x2*y1*y2) 35 | return [x3 % q,y3 % q] 36 | 37 | def radix255(x): 38 | x = x % q 39 | if x + x > q: x -= q 40 | x = [x,0,0,0,0,0,0,0,0,0] 41 | bits = [26,25,26,25,26,25,26,25,26,25] 42 | for i in range(9): 43 | carry = (x[i] + 2**(bits[i]-1)) / 2**bits[i] 44 | x[i] -= carry * 2**bits[i] 45 | x[i + 1] += carry 46 | result = "" 47 | for i in range(9): 48 | result = result+str(x[i])+"," 49 | result = result+str(x[9]) 50 | return result 51 | 52 | Bi = B 53 | for i in range(32): 54 | print "{" 55 | Bij = Bi 56 | for j in range(8): 57 | print " {" 58 | print " {",radix255(Bij[1]+Bij[0]),"}," 59 | print " {",radix255(Bij[1]-Bij[0]),"}," 60 | print " {",radix255(2*d*Bij[0]*Bij[1]),"}," 61 | Bij = edwards(Bij,Bi) 62 | print " }," 63 | print "}," 64 | for k in range(8): 65 | Bi = edwards(Bi,Bi) 66 | -------------------------------------------------------------------------------- /ed25519-supercop/ref10/base2.h: -------------------------------------------------------------------------------- 1 | { 2 | { 25967493,-14356035,29566456,3660896,-12694345,4014787,27544626,-11754271,-6079156,2047605 }, 3 | { -12545711,934262,-2722910,3049990,-727428,9406986,12720692,5043384,19500929,-15469378 }, 4 | { -8738181,4489570,9688441,-14785194,10184609,-12363380,29287919,11864899,-24514362,-4438546 }, 5 | }, 6 | { 7 | { 15636291,-9688557,24204773,-7912398,616977,-16685262,27787600,-14772189,28944400,-1550024 }, 8 | { 16568933,4717097,-11556148,-1102322,15682896,-11807043,16354577,-11775962,7689662,11199574 }, 9 | { 30464156,-5976125,-11779434,-15670865,23220365,15915852,7512774,10017326,-17749093,-9920357 }, 10 | }, 11 | { 12 | { 10861363,11473154,27284546,1981175,-30064349,12577861,32867885,14515107,-15438304,10819380 }, 13 | { 4708026,6336745,20377586,9066809,-11272109,6594696,-25653668,12483688,-12668491,5581306 }, 14 | { 19563160,16186464,-29386857,4097519,10237984,-4348115,28542350,13850243,-23678021,-15815942 }, 15 | }, 16 | { 17 | { 5153746,9909285,1723747,-2777874,30523605,5516873,19480852,5230134,-23952439,-15175766 }, 18 | { -30269007,-3463509,7665486,10083793,28475525,1649722,20654025,16520125,30598449,7715701 }, 19 | { 28881845,14381568,9657904,3680757,-20181635,7843316,-31400660,1370708,29794553,-1409300 }, 20 | }, 21 | { 22 | { -22518993,-6692182,14201702,-8745502,-23510406,8844726,18474211,-1361450,-13062696,13821877 }, 23 | { -6455177,-7839871,3374702,-4740862,-27098617,-10571707,31655028,-7212327,18853322,-14220951 }, 24 | { 4566830,-12963868,-28974889,-12240689,-7602672,-2830569,-8514358,-10431137,2207753,-3209784 }, 25 | }, 26 | { 27 | { -25154831,-4185821,29681144,7868801,-6854661,-9423865,-12437364,-663000,-31111463,-16132436 }, 28 | { 25576264,-2703214,7349804,-11814844,16472782,9300885,3844789,15725684,171356,6466918 }, 29 | { 23103977,13316479,9739013,-16149481,817875,-15038942,8965339,-14088058,-30714912,16193877 }, 30 | }, 31 | { 32 | { -33521811,3180713,-2394130,14003687,-16903474,-16270840,17238398,4729455,-18074513,9256800 }, 33 | { -25182317,-4174131,32336398,5036987,-21236817,11360617,22616405,9761698,-19827198,630305 }, 34 | { -13720693,2639453,-24237460,-7406481,9494427,-5774029,-6554551,-15960994,-2449256,-14291300 }, 35 | }, 36 | { 37 | { -3151181,-5046075,9282714,6866145,-31907062,-863023,-18940575,15033784,25105118,-7894876 }, 38 | { -24326370,15950226,-31801215,-14592823,-11662737,-5090925,1573892,-2625887,2198790,-15804619 }, 39 | { -3099351,10324967,-2241613,7453183,-5446979,-2735503,-13812022,-16236442,-32461234,-12290683 }, 40 | }, 41 | -------------------------------------------------------------------------------- /ed25519-supercop/ref10/base2.py: -------------------------------------------------------------------------------- 1 | b = 256 2 | q = 2**255 - 19 3 | l = 2**252 + 27742317777372353535851937790883648493 4 | 5 | def expmod(b,e,m): 6 | if e == 0: return 1 7 | t = expmod(b,e/2,m)**2 % m 8 | if e & 1: t = (t*b) % m 9 | return t 10 | 11 | def inv(x): 12 | return expmod(x,q-2,q) 13 | 14 | d = -121665 * inv(121666) 15 | I = expmod(2,(q-1)/4,q) 16 | 17 | def xrecover(y): 18 | xx = (y*y-1) * inv(d*y*y+1) 19 | x = expmod(xx,(q+3)/8,q) 20 | if (x*x - xx) % q != 0: x = (x*I) % q 21 | if x % 2 != 0: x = q-x 22 | return x 23 | 24 | By = 4 * inv(5) 25 | Bx = xrecover(By) 26 | B = [Bx % q,By % q] 27 | 28 | def edwards(P,Q): 29 | x1 = P[0] 30 | y1 = P[1] 31 | x2 = Q[0] 32 | y2 = Q[1] 33 | x3 = (x1*y2+x2*y1) * inv(1+d*x1*x2*y1*y2) 34 | y3 = (y1*y2+x1*x2) * inv(1-d*x1*x2*y1*y2) 35 | return [x3 % q,y3 % q] 36 | 37 | def radix255(x): 38 | x = x % q 39 | if x + x > q: x -= q 40 | x = [x,0,0,0,0,0,0,0,0,0] 41 | bits = [26,25,26,25,26,25,26,25,26,25] 42 | for i in range(9): 43 | carry = (x[i] + 2**(bits[i]-1)) / 2**bits[i] 44 | x[i] -= carry * 2**bits[i] 45 | x[i + 1] += carry 46 | result = "" 47 | for i in range(9): 48 | result = result+str(x[i])+"," 49 | result = result+str(x[9]) 50 | return result 51 | 52 | Bi = B 53 | 54 | for i in range(8): 55 | print " {" 56 | print " {",radix255(Bi[1]+Bi[0]),"}," 57 | print " {",radix255(Bi[1]-Bi[0]),"}," 58 | print " {",radix255(2*d*Bi[0]*Bi[1]),"}," 59 | print " }," 60 | Bi = edwards(B,edwards(B,Bi)) 61 | -------------------------------------------------------------------------------- /ed25519-supercop/ref10/d.h: -------------------------------------------------------------------------------- 1 | -10913610,13857413,-15372611,6949391,114729,-8787816,-6275908,-3247719,-18696448,-12055116 2 | -------------------------------------------------------------------------------- /ed25519-supercop/ref10/d.py: -------------------------------------------------------------------------------- 1 | q = 2**255 - 19 2 | 3 | def expmod(b,e,m): 4 | if e == 0: return 1 5 | t = expmod(b,e/2,m)**2 % m 6 | if e & 1: t = (t*b) % m 7 | return t 8 | 9 | def inv(x): 10 | return expmod(x,q-2,q) 11 | 12 | def radix255(x): 13 | x = x % q 14 | if x + x > q: x -= q 15 | x = [x,0,0,0,0,0,0,0,0,0] 16 | bits = [26,25,26,25,26,25,26,25,26,25] 17 | for i in range(9): 18 | carry = (x[i] + 2**(bits[i]-1)) / 2**bits[i] 19 | x[i] -= carry * 2**bits[i] 20 | x[i + 1] += carry 21 | result = "" 22 | for i in range(9): 23 | result = result+str(x[i])+"," 24 | result = result+str(x[9]) 25 | return result 26 | 27 | d = -121665 * inv(121666) 28 | print radix255(d) 29 | -------------------------------------------------------------------------------- /ed25519-supercop/ref10/d2.h: -------------------------------------------------------------------------------- 1 | -21827239,-5839606,-30745221,13898782,229458,15978800,-12551817,-6495438,29715968,9444199 2 | -------------------------------------------------------------------------------- /ed25519-supercop/ref10/d2.py: -------------------------------------------------------------------------------- 1 | q = 2**255 - 19 2 | 3 | def expmod(b,e,m): 4 | if e == 0: return 1 5 | t = expmod(b,e/2,m)**2 % m 6 | if e & 1: t = (t*b) % m 7 | return t 8 | 9 | def inv(x): 10 | return expmod(x,q-2,q) 11 | 12 | def radix255(x): 13 | x = x % q 14 | if x + x > q: x -= q 15 | x = [x,0,0,0,0,0,0,0,0,0] 16 | bits = [26,25,26,25,26,25,26,25,26,25] 17 | for i in range(9): 18 | carry = (x[i] + 2**(bits[i]-1)) / 2**bits[i] 19 | x[i] -= carry * 2**bits[i] 20 | x[i + 1] += carry 21 | result = "" 22 | for i in range(9): 23 | result = result+str(x[i])+"," 24 | result = result+str(x[9]) 25 | return result 26 | 27 | d = -121665 * inv(121666) 28 | print radix255(d*2) 29 | -------------------------------------------------------------------------------- /ed25519-supercop/ref10/fe.h: -------------------------------------------------------------------------------- 1 | #ifndef FE_H 2 | #define FE_H 3 | 4 | #include "crypto_int32.h" 5 | 6 | typedef crypto_int32 fe[10]; 7 | 8 | /* 9 | fe means field element. 10 | Here the field is \Z/(2^255-19). 11 | An element t, entries t[0]...t[9], represents the integer 12 | t[0]+2^26 t[1]+2^51 t[2]+2^77 t[3]+2^102 t[4]+...+2^230 t[9]. 13 | Bounds on each t[i] vary depending on context. 14 | */ 15 | 16 | #define fe_frombytes crypto_sign_ed25519_ref10_fe_frombytes 17 | #define fe_tobytes crypto_sign_ed25519_ref10_fe_tobytes 18 | #define fe_copy crypto_sign_ed25519_ref10_fe_copy 19 | #define fe_isnonzero crypto_sign_ed25519_ref10_fe_isnonzero 20 | #define fe_isnegative crypto_sign_ed25519_ref10_fe_isnegative 21 | #define fe_0 crypto_sign_ed25519_ref10_fe_0 22 | #define fe_1 crypto_sign_ed25519_ref10_fe_1 23 | #define fe_cswap crypto_sign_ed25519_ref10_fe_cswap 24 | #define fe_cmov crypto_sign_ed25519_ref10_fe_cmov 25 | #define fe_add crypto_sign_ed25519_ref10_fe_add 26 | #define fe_sub crypto_sign_ed25519_ref10_fe_sub 27 | #define fe_neg crypto_sign_ed25519_ref10_fe_neg 28 | #define fe_mul crypto_sign_ed25519_ref10_fe_mul 29 | #define fe_sq crypto_sign_ed25519_ref10_fe_sq 30 | #define fe_sq2 crypto_sign_ed25519_ref10_fe_sq2 31 | #define fe_mul121666 crypto_sign_ed25519_ref10_fe_mul121666 32 | #define fe_invert crypto_sign_ed25519_ref10_fe_invert 33 | #define fe_pow22523 crypto_sign_ed25519_ref10_fe_pow22523 34 | 35 | extern void fe_frombytes(fe,const unsigned char *); 36 | extern void fe_tobytes(unsigned char *,const fe); 37 | 38 | extern void fe_copy(fe,const fe); 39 | extern int fe_isnonzero(const fe); 40 | extern int fe_isnegative(const fe); 41 | extern void fe_0(fe); 42 | extern void fe_1(fe); 43 | extern void fe_cswap(fe,fe,unsigned int); 44 | extern void fe_cmov(fe,const fe,unsigned int); 45 | 46 | extern void fe_add(fe,const fe,const fe); 47 | extern void fe_sub(fe,const fe,const fe); 48 | extern void fe_neg(fe,const fe); 49 | extern void fe_mul(fe,const fe,const fe); 50 | extern void fe_sq(fe,const fe); 51 | extern void fe_sq2(fe,const fe); 52 | extern void fe_mul121666(fe,const fe); 53 | extern void fe_invert(fe,const fe); 54 | extern void fe_pow22523(fe,const fe); 55 | 56 | #endif 57 | -------------------------------------------------------------------------------- /ed25519-supercop/ref10/fe_0.c: -------------------------------------------------------------------------------- 1 | #include "fe.h" 2 | 3 | /* 4 | h = 0 5 | */ 6 | 7 | void fe_0(fe h) 8 | { 9 | h[0] = 0; 10 | h[1] = 0; 11 | h[2] = 0; 12 | h[3] = 0; 13 | h[4] = 0; 14 | h[5] = 0; 15 | h[6] = 0; 16 | h[7] = 0; 17 | h[8] = 0; 18 | h[9] = 0; 19 | } 20 | -------------------------------------------------------------------------------- /ed25519-supercop/ref10/fe_1.c: -------------------------------------------------------------------------------- 1 | #include "fe.h" 2 | 3 | /* 4 | h = 1 5 | */ 6 | 7 | void fe_1(fe h) 8 | { 9 | h[0] = 1; 10 | h[1] = 0; 11 | h[2] = 0; 12 | h[3] = 0; 13 | h[4] = 0; 14 | h[5] = 0; 15 | h[6] = 0; 16 | h[7] = 0; 17 | h[8] = 0; 18 | h[9] = 0; 19 | } 20 | -------------------------------------------------------------------------------- /ed25519-supercop/ref10/fe_add.c: -------------------------------------------------------------------------------- 1 | #include "fe.h" 2 | 3 | /* 4 | h = f + g 5 | Can overlap h with f or g. 6 | 7 | Preconditions: 8 | |f| bounded by 1.1*2^25,1.1*2^24,1.1*2^25,1.1*2^24,etc. 9 | |g| bounded by 1.1*2^25,1.1*2^24,1.1*2^25,1.1*2^24,etc. 10 | 11 | Postconditions: 12 | |h| bounded by 1.1*2^26,1.1*2^25,1.1*2^26,1.1*2^25,etc. 13 | */ 14 | 15 | void fe_add(fe h,const fe f,const fe g) 16 | { 17 | crypto_int32 f0 = f[0]; 18 | crypto_int32 f1 = f[1]; 19 | crypto_int32 f2 = f[2]; 20 | crypto_int32 f3 = f[3]; 21 | crypto_int32 f4 = f[4]; 22 | crypto_int32 f5 = f[5]; 23 | crypto_int32 f6 = f[6]; 24 | crypto_int32 f7 = f[7]; 25 | crypto_int32 f8 = f[8]; 26 | crypto_int32 f9 = f[9]; 27 | crypto_int32 g0 = g[0]; 28 | crypto_int32 g1 = g[1]; 29 | crypto_int32 g2 = g[2]; 30 | crypto_int32 g3 = g[3]; 31 | crypto_int32 g4 = g[4]; 32 | crypto_int32 g5 = g[5]; 33 | crypto_int32 g6 = g[6]; 34 | crypto_int32 g7 = g[7]; 35 | crypto_int32 g8 = g[8]; 36 | crypto_int32 g9 = g[9]; 37 | crypto_int32 h0 = f0 + g0; 38 | crypto_int32 h1 = f1 + g1; 39 | crypto_int32 h2 = f2 + g2; 40 | crypto_int32 h3 = f3 + g3; 41 | crypto_int32 h4 = f4 + g4; 42 | crypto_int32 h5 = f5 + g5; 43 | crypto_int32 h6 = f6 + g6; 44 | crypto_int32 h7 = f7 + g7; 45 | crypto_int32 h8 = f8 + g8; 46 | crypto_int32 h9 = f9 + g9; 47 | h[0] = h0; 48 | h[1] = h1; 49 | h[2] = h2; 50 | h[3] = h3; 51 | h[4] = h4; 52 | h[5] = h5; 53 | h[6] = h6; 54 | h[7] = h7; 55 | h[8] = h8; 56 | h[9] = h9; 57 | } 58 | -------------------------------------------------------------------------------- /ed25519-supercop/ref10/fe_cmov.c: -------------------------------------------------------------------------------- 1 | #include "fe.h" 2 | 3 | /* 4 | Replace (f,g) with (g,g) if b == 1; 5 | replace (f,g) with (f,g) if b == 0. 6 | 7 | Preconditions: b in {0,1}. 8 | */ 9 | 10 | void fe_cmov(fe f,const fe g,unsigned int b) 11 | { 12 | crypto_int32 f0 = f[0]; 13 | crypto_int32 f1 = f[1]; 14 | crypto_int32 f2 = f[2]; 15 | crypto_int32 f3 = f[3]; 16 | crypto_int32 f4 = f[4]; 17 | crypto_int32 f5 = f[5]; 18 | crypto_int32 f6 = f[6]; 19 | crypto_int32 f7 = f[7]; 20 | crypto_int32 f8 = f[8]; 21 | crypto_int32 f9 = f[9]; 22 | crypto_int32 g0 = g[0]; 23 | crypto_int32 g1 = g[1]; 24 | crypto_int32 g2 = g[2]; 25 | crypto_int32 g3 = g[3]; 26 | crypto_int32 g4 = g[4]; 27 | crypto_int32 g5 = g[5]; 28 | crypto_int32 g6 = g[6]; 29 | crypto_int32 g7 = g[7]; 30 | crypto_int32 g8 = g[8]; 31 | crypto_int32 g9 = g[9]; 32 | crypto_int32 x0 = f0 ^ g0; 33 | crypto_int32 x1 = f1 ^ g1; 34 | crypto_int32 x2 = f2 ^ g2; 35 | crypto_int32 x3 = f3 ^ g3; 36 | crypto_int32 x4 = f4 ^ g4; 37 | crypto_int32 x5 = f5 ^ g5; 38 | crypto_int32 x6 = f6 ^ g6; 39 | crypto_int32 x7 = f7 ^ g7; 40 | crypto_int32 x8 = f8 ^ g8; 41 | crypto_int32 x9 = f9 ^ g9; 42 | b = -b; 43 | x0 &= b; 44 | x1 &= b; 45 | x2 &= b; 46 | x3 &= b; 47 | x4 &= b; 48 | x5 &= b; 49 | x6 &= b; 50 | x7 &= b; 51 | x8 &= b; 52 | x9 &= b; 53 | f[0] = f0 ^ x0; 54 | f[1] = f1 ^ x1; 55 | f[2] = f2 ^ x2; 56 | f[3] = f3 ^ x3; 57 | f[4] = f4 ^ x4; 58 | f[5] = f5 ^ x5; 59 | f[6] = f6 ^ x6; 60 | f[7] = f7 ^ x7; 61 | f[8] = f8 ^ x8; 62 | f[9] = f9 ^ x9; 63 | } 64 | -------------------------------------------------------------------------------- /ed25519-supercop/ref10/fe_copy.c: -------------------------------------------------------------------------------- 1 | #include "fe.h" 2 | 3 | /* 4 | h = f 5 | */ 6 | 7 | void fe_copy(fe h,const fe f) 8 | { 9 | crypto_int32 f0 = f[0]; 10 | crypto_int32 f1 = f[1]; 11 | crypto_int32 f2 = f[2]; 12 | crypto_int32 f3 = f[3]; 13 | crypto_int32 f4 = f[4]; 14 | crypto_int32 f5 = f[5]; 15 | crypto_int32 f6 = f[6]; 16 | crypto_int32 f7 = f[7]; 17 | crypto_int32 f8 = f[8]; 18 | crypto_int32 f9 = f[9]; 19 | h[0] = f0; 20 | h[1] = f1; 21 | h[2] = f2; 22 | h[3] = f3; 23 | h[4] = f4; 24 | h[5] = f5; 25 | h[6] = f6; 26 | h[7] = f7; 27 | h[8] = f8; 28 | h[9] = f9; 29 | } 30 | -------------------------------------------------------------------------------- /ed25519-supercop/ref10/fe_frombytes.c: -------------------------------------------------------------------------------- 1 | #include "fe.h" 2 | #include "crypto_int64.h" 3 | #include "crypto_uint64.h" 4 | 5 | static crypto_uint64 load_3(const unsigned char *in) 6 | { 7 | crypto_uint64 result; 8 | result = (crypto_uint64) in[0]; 9 | result |= ((crypto_uint64) in[1]) << 8; 10 | result |= ((crypto_uint64) in[2]) << 16; 11 | return result; 12 | } 13 | 14 | static crypto_uint64 load_4(const unsigned char *in) 15 | { 16 | crypto_uint64 result; 17 | result = (crypto_uint64) in[0]; 18 | result |= ((crypto_uint64) in[1]) << 8; 19 | result |= ((crypto_uint64) in[2]) << 16; 20 | result |= ((crypto_uint64) in[3]) << 24; 21 | return result; 22 | } 23 | 24 | /* 25 | Ignores top bit of h. 26 | */ 27 | 28 | void fe_frombytes(fe h,const unsigned char *s) 29 | { 30 | crypto_int64 h0 = load_4(s); 31 | crypto_int64 h1 = load_3(s + 4) << 6; 32 | crypto_int64 h2 = load_3(s + 7) << 5; 33 | crypto_int64 h3 = load_3(s + 10) << 3; 34 | crypto_int64 h4 = load_3(s + 13) << 2; 35 | crypto_int64 h5 = load_4(s + 16); 36 | crypto_int64 h6 = load_3(s + 20) << 7; 37 | crypto_int64 h7 = load_3(s + 23) << 5; 38 | crypto_int64 h8 = load_3(s + 26) << 4; 39 | crypto_int64 h9 = (load_3(s + 29) & 8388607) << 2; 40 | crypto_int64 carry0; 41 | crypto_int64 carry1; 42 | crypto_int64 carry2; 43 | crypto_int64 carry3; 44 | crypto_int64 carry4; 45 | crypto_int64 carry5; 46 | crypto_int64 carry6; 47 | crypto_int64 carry7; 48 | crypto_int64 carry8; 49 | crypto_int64 carry9; 50 | 51 | carry9 = (h9 + (crypto_int64) (1<<24)) >> 25; h0 += carry9 * 19; h9 -= carry9 << 25; 52 | carry1 = (h1 + (crypto_int64) (1<<24)) >> 25; h2 += carry1; h1 -= carry1 << 25; 53 | carry3 = (h3 + (crypto_int64) (1<<24)) >> 25; h4 += carry3; h3 -= carry3 << 25; 54 | carry5 = (h5 + (crypto_int64) (1<<24)) >> 25; h6 += carry5; h5 -= carry5 << 25; 55 | carry7 = (h7 + (crypto_int64) (1<<24)) >> 25; h8 += carry7; h7 -= carry7 << 25; 56 | 57 | carry0 = (h0 + (crypto_int64) (1<<25)) >> 26; h1 += carry0; h0 -= carry0 << 26; 58 | carry2 = (h2 + (crypto_int64) (1<<25)) >> 26; h3 += carry2; h2 -= carry2 << 26; 59 | carry4 = (h4 + (crypto_int64) (1<<25)) >> 26; h5 += carry4; h4 -= carry4 << 26; 60 | carry6 = (h6 + (crypto_int64) (1<<25)) >> 26; h7 += carry6; h6 -= carry6 << 26; 61 | carry8 = (h8 + (crypto_int64) (1<<25)) >> 26; h9 += carry8; h8 -= carry8 << 26; 62 | 63 | h[0] = h0; 64 | h[1] = h1; 65 | h[2] = h2; 66 | h[3] = h3; 67 | h[4] = h4; 68 | h[5] = h5; 69 | h[6] = h6; 70 | h[7] = h7; 71 | h[8] = h8; 72 | h[9] = h9; 73 | } 74 | -------------------------------------------------------------------------------- /ed25519-supercop/ref10/fe_invert.c: -------------------------------------------------------------------------------- 1 | #include "fe.h" 2 | 3 | void fe_invert(fe out,const fe z) 4 | { 5 | fe t0; 6 | fe t1; 7 | fe t2; 8 | fe t3; 9 | int i; 10 | 11 | #include "pow225521.h" 12 | 13 | return; 14 | } 15 | -------------------------------------------------------------------------------- /ed25519-supercop/ref10/fe_isnegative.c: -------------------------------------------------------------------------------- 1 | #include "fe.h" 2 | 3 | /* 4 | return 1 if f is in {1,3,5,...,q-2} 5 | return 0 if f is in {0,2,4,...,q-1} 6 | 7 | Preconditions: 8 | |f| bounded by 1.1*2^26,1.1*2^25,1.1*2^26,1.1*2^25,etc. 9 | */ 10 | 11 | int fe_isnegative(const fe f) 12 | { 13 | unsigned char s[32]; 14 | fe_tobytes(s,f); 15 | return s[0] & 1; 16 | } 17 | -------------------------------------------------------------------------------- /ed25519-supercop/ref10/fe_isnonzero.c: -------------------------------------------------------------------------------- 1 | #include "fe.h" 2 | #include "crypto_verify_32.h" 3 | 4 | /* 5 | return 1 if f == 0 6 | return 0 if f != 0 7 | 8 | Preconditions: 9 | |f| bounded by 1.1*2^26,1.1*2^25,1.1*2^26,1.1*2^25,etc. 10 | */ 11 | 12 | static const unsigned char zero[32]; 13 | 14 | int fe_isnonzero(const fe f) 15 | { 16 | unsigned char s[32]; 17 | fe_tobytes(s,f); 18 | return crypto_verify_32(s,zero); 19 | } 20 | -------------------------------------------------------------------------------- /ed25519-supercop/ref10/fe_neg.c: -------------------------------------------------------------------------------- 1 | #include "fe.h" 2 | 3 | /* 4 | h = -f 5 | 6 | Preconditions: 7 | |f| bounded by 1.1*2^25,1.1*2^24,1.1*2^25,1.1*2^24,etc. 8 | 9 | Postconditions: 10 | |h| bounded by 1.1*2^25,1.1*2^24,1.1*2^25,1.1*2^24,etc. 11 | */ 12 | 13 | void fe_neg(fe h,const fe f) 14 | { 15 | crypto_int32 f0 = f[0]; 16 | crypto_int32 f1 = f[1]; 17 | crypto_int32 f2 = f[2]; 18 | crypto_int32 f3 = f[3]; 19 | crypto_int32 f4 = f[4]; 20 | crypto_int32 f5 = f[5]; 21 | crypto_int32 f6 = f[6]; 22 | crypto_int32 f7 = f[7]; 23 | crypto_int32 f8 = f[8]; 24 | crypto_int32 f9 = f[9]; 25 | crypto_int32 h0 = -f0; 26 | crypto_int32 h1 = -f1; 27 | crypto_int32 h2 = -f2; 28 | crypto_int32 h3 = -f3; 29 | crypto_int32 h4 = -f4; 30 | crypto_int32 h5 = -f5; 31 | crypto_int32 h6 = -f6; 32 | crypto_int32 h7 = -f7; 33 | crypto_int32 h8 = -f8; 34 | crypto_int32 h9 = -f9; 35 | h[0] = h0; 36 | h[1] = h1; 37 | h[2] = h2; 38 | h[3] = h3; 39 | h[4] = h4; 40 | h[5] = h5; 41 | h[6] = h6; 42 | h[7] = h7; 43 | h[8] = h8; 44 | h[9] = h9; 45 | } 46 | -------------------------------------------------------------------------------- /ed25519-supercop/ref10/fe_pow22523.c: -------------------------------------------------------------------------------- 1 | #include "fe.h" 2 | 3 | void fe_pow22523(fe out,const fe z) 4 | { 5 | fe t0; 6 | fe t1; 7 | fe t2; 8 | int i; 9 | 10 | #include "pow22523.h" 11 | 12 | return; 13 | } 14 | -------------------------------------------------------------------------------- /ed25519-supercop/ref10/fe_sub.c: -------------------------------------------------------------------------------- 1 | #include "fe.h" 2 | 3 | /* 4 | h = f - g 5 | Can overlap h with f or g. 6 | 7 | Preconditions: 8 | |f| bounded by 1.1*2^25,1.1*2^24,1.1*2^25,1.1*2^24,etc. 9 | |g| bounded by 1.1*2^25,1.1*2^24,1.1*2^25,1.1*2^24,etc. 10 | 11 | Postconditions: 12 | |h| bounded by 1.1*2^26,1.1*2^25,1.1*2^26,1.1*2^25,etc. 13 | */ 14 | 15 | void fe_sub(fe h,const fe f,const fe g) 16 | { 17 | crypto_int32 f0 = f[0]; 18 | crypto_int32 f1 = f[1]; 19 | crypto_int32 f2 = f[2]; 20 | crypto_int32 f3 = f[3]; 21 | crypto_int32 f4 = f[4]; 22 | crypto_int32 f5 = f[5]; 23 | crypto_int32 f6 = f[6]; 24 | crypto_int32 f7 = f[7]; 25 | crypto_int32 f8 = f[8]; 26 | crypto_int32 f9 = f[9]; 27 | crypto_int32 g0 = g[0]; 28 | crypto_int32 g1 = g[1]; 29 | crypto_int32 g2 = g[2]; 30 | crypto_int32 g3 = g[3]; 31 | crypto_int32 g4 = g[4]; 32 | crypto_int32 g5 = g[5]; 33 | crypto_int32 g6 = g[6]; 34 | crypto_int32 g7 = g[7]; 35 | crypto_int32 g8 = g[8]; 36 | crypto_int32 g9 = g[9]; 37 | crypto_int32 h0 = f0 - g0; 38 | crypto_int32 h1 = f1 - g1; 39 | crypto_int32 h2 = f2 - g2; 40 | crypto_int32 h3 = f3 - g3; 41 | crypto_int32 h4 = f4 - g4; 42 | crypto_int32 h5 = f5 - g5; 43 | crypto_int32 h6 = f6 - g6; 44 | crypto_int32 h7 = f7 - g7; 45 | crypto_int32 h8 = f8 - g8; 46 | crypto_int32 h9 = f9 - g9; 47 | h[0] = h0; 48 | h[1] = h1; 49 | h[2] = h2; 50 | h[3] = h3; 51 | h[4] = h4; 52 | h[5] = h5; 53 | h[6] = h6; 54 | h[7] = h7; 55 | h[8] = h8; 56 | h[9] = h9; 57 | } 58 | -------------------------------------------------------------------------------- /ed25519-supercop/ref10/ge.h: -------------------------------------------------------------------------------- 1 | #ifndef GE_H 2 | #define GE_H 3 | 4 | /* 5 | ge means group element. 6 | 7 | Here the group is the set of pairs (x,y) of field elements (see fe.h) 8 | satisfying -x^2 + y^2 = 1 + d x^2y^2 9 | where d = -121665/121666. 10 | 11 | Representations: 12 | ge_p2 (projective): (X:Y:Z) satisfying x=X/Z, y=Y/Z 13 | ge_p3 (extended): (X:Y:Z:T) satisfying x=X/Z, y=Y/Z, XY=ZT 14 | ge_p1p1 (completed): ((X:Z),(Y:T)) satisfying x=X/Z, y=Y/T 15 | ge_precomp (Duif): (y+x,y-x,2dxy) 16 | */ 17 | 18 | #include "fe.h" 19 | 20 | typedef struct { 21 | fe X; 22 | fe Y; 23 | fe Z; 24 | } ge_p2; 25 | 26 | typedef struct { 27 | fe X; 28 | fe Y; 29 | fe Z; 30 | fe T; 31 | } ge_p3; 32 | 33 | typedef struct { 34 | fe X; 35 | fe Y; 36 | fe Z; 37 | fe T; 38 | } ge_p1p1; 39 | 40 | typedef struct { 41 | fe yplusx; 42 | fe yminusx; 43 | fe xy2d; 44 | } ge_precomp; 45 | 46 | typedef struct { 47 | fe YplusX; 48 | fe YminusX; 49 | fe Z; 50 | fe T2d; 51 | } ge_cached; 52 | 53 | #define ge_frombytes_negate_vartime crypto_sign_ed25519_ref10_ge_frombytes_negate_vartime 54 | #define ge_tobytes crypto_sign_ed25519_ref10_ge_tobytes 55 | #define ge_p3_tobytes crypto_sign_ed25519_ref10_ge_p3_tobytes 56 | 57 | #define ge_p2_0 crypto_sign_ed25519_ref10_ge_p2_0 58 | #define ge_p3_0 crypto_sign_ed25519_ref10_ge_p3_0 59 | #define ge_precomp_0 crypto_sign_ed25519_ref10_ge_precomp_0 60 | #define ge_p3_to_p2 crypto_sign_ed25519_ref10_ge_p3_to_p2 61 | #define ge_p3_to_cached crypto_sign_ed25519_ref10_ge_p3_to_cached 62 | #define ge_p1p1_to_p2 crypto_sign_ed25519_ref10_ge_p1p1_to_p2 63 | #define ge_p1p1_to_p3 crypto_sign_ed25519_ref10_ge_p1p1_to_p3 64 | #define ge_p2_dbl crypto_sign_ed25519_ref10_ge_p2_dbl 65 | #define ge_p3_dbl crypto_sign_ed25519_ref10_ge_p3_dbl 66 | 67 | #define ge_madd crypto_sign_ed25519_ref10_ge_madd 68 | #define ge_msub crypto_sign_ed25519_ref10_ge_msub 69 | #define ge_add crypto_sign_ed25519_ref10_ge_add 70 | #define ge_sub crypto_sign_ed25519_ref10_ge_sub 71 | #define ge_scalarmult_base crypto_sign_ed25519_ref10_ge_scalarmult_base 72 | #define ge_double_scalarmult_vartime crypto_sign_ed25519_ref10_ge_double_scalarmult_vartime 73 | 74 | extern void ge_tobytes(unsigned char *,const ge_p2 *); 75 | extern void ge_p3_tobytes(unsigned char *,const ge_p3 *); 76 | extern int ge_frombytes_negate_vartime(ge_p3 *,const unsigned char *); 77 | 78 | extern void ge_p2_0(ge_p2 *); 79 | extern void ge_p3_0(ge_p3 *); 80 | extern void ge_precomp_0(ge_precomp *); 81 | extern void ge_p3_to_p2(ge_p2 *,const ge_p3 *); 82 | extern void ge_p3_to_cached(ge_cached *,const ge_p3 *); 83 | extern void ge_p1p1_to_p2(ge_p2 *,const ge_p1p1 *); 84 | extern void ge_p1p1_to_p3(ge_p3 *,const ge_p1p1 *); 85 | extern void ge_p2_dbl(ge_p1p1 *,const ge_p2 *); 86 | extern void ge_p3_dbl(ge_p1p1 *,const ge_p3 *); 87 | 88 | extern void ge_madd(ge_p1p1 *,const ge_p3 *,const ge_precomp *); 89 | extern void ge_msub(ge_p1p1 *,const ge_p3 *,const ge_precomp *); 90 | extern void ge_add(ge_p1p1 *,const ge_p3 *,const ge_cached *); 91 | extern void ge_sub(ge_p1p1 *,const ge_p3 *,const ge_cached *); 92 | extern void ge_scalarmult_base(ge_p3 *,const unsigned char *); 93 | extern void ge_double_scalarmult_vartime(ge_p2 *,const unsigned char *,const ge_p3 *,const unsigned char *); 94 | 95 | #endif 96 | -------------------------------------------------------------------------------- /ed25519-supercop/ref10/ge_add.c: -------------------------------------------------------------------------------- 1 | #include "ge.h" 2 | 3 | /* 4 | r = p + q 5 | */ 6 | 7 | void ge_add(ge_p1p1 *r,const ge_p3 *p,const ge_cached *q) 8 | { 9 | fe t0; 10 | #include "ge_add.h" 11 | } 12 | -------------------------------------------------------------------------------- /ed25519-supercop/ref10/ge_add.h: -------------------------------------------------------------------------------- 1 | 2 | /* qhasm: enter ge_add */ 3 | 4 | /* qhasm: fe X1 */ 5 | 6 | /* qhasm: fe Y1 */ 7 | 8 | /* qhasm: fe Z1 */ 9 | 10 | /* qhasm: fe Z2 */ 11 | 12 | /* qhasm: fe T1 */ 13 | 14 | /* qhasm: fe ZZ */ 15 | 16 | /* qhasm: fe YpX2 */ 17 | 18 | /* qhasm: fe YmX2 */ 19 | 20 | /* qhasm: fe T2d2 */ 21 | 22 | /* qhasm: fe X3 */ 23 | 24 | /* qhasm: fe Y3 */ 25 | 26 | /* qhasm: fe Z3 */ 27 | 28 | /* qhasm: fe T3 */ 29 | 30 | /* qhasm: fe YpX1 */ 31 | 32 | /* qhasm: fe YmX1 */ 33 | 34 | /* qhasm: fe A */ 35 | 36 | /* qhasm: fe B */ 37 | 38 | /* qhasm: fe C */ 39 | 40 | /* qhasm: fe D */ 41 | 42 | /* qhasm: YpX1 = Y1+X1 */ 43 | /* asm 1: fe_add(>YpX1=fe#1,YpX1=r->X,Y,X); */ 45 | fe_add(r->X,p->Y,p->X); 46 | 47 | /* qhasm: YmX1 = Y1-X1 */ 48 | /* asm 1: fe_sub(>YmX1=fe#2,YmX1=r->Y,Y,X); */ 50 | fe_sub(r->Y,p->Y,p->X); 51 | 52 | /* qhasm: A = YpX1*YpX2 */ 53 | /* asm 1: fe_mul(>A=fe#3,A=r->Z,X,YplusX); */ 55 | fe_mul(r->Z,r->X,q->YplusX); 56 | 57 | /* qhasm: B = YmX1*YmX2 */ 58 | /* asm 1: fe_mul(>B=fe#2,B=r->Y,Y,YminusX); */ 60 | fe_mul(r->Y,r->Y,q->YminusX); 61 | 62 | /* qhasm: C = T2d2*T1 */ 63 | /* asm 1: fe_mul(>C=fe#4,C=r->T,T2d,T); */ 65 | fe_mul(r->T,q->T2d,p->T); 66 | 67 | /* qhasm: ZZ = Z1*Z2 */ 68 | /* asm 1: fe_mul(>ZZ=fe#1,ZZ=r->X,Z,Z); */ 70 | fe_mul(r->X,p->Z,q->Z); 71 | 72 | /* qhasm: D = 2*ZZ */ 73 | /* asm 1: fe_add(>D=fe#5,D=t0,X,X); */ 75 | fe_add(t0,r->X,r->X); 76 | 77 | /* qhasm: X3 = A-B */ 78 | /* asm 1: fe_sub(>X3=fe#1,X3=r->X,Z,Y); */ 80 | fe_sub(r->X,r->Z,r->Y); 81 | 82 | /* qhasm: Y3 = A+B */ 83 | /* asm 1: fe_add(>Y3=fe#2,Y3=r->Y,Z,Y); */ 85 | fe_add(r->Y,r->Z,r->Y); 86 | 87 | /* qhasm: Z3 = D+C */ 88 | /* asm 1: fe_add(>Z3=fe#3,Z3=r->Z,T); */ 90 | fe_add(r->Z,t0,r->T); 91 | 92 | /* qhasm: T3 = D-C */ 93 | /* asm 1: fe_sub(>T3=fe#4,T3=r->T,T); */ 95 | fe_sub(r->T,t0,r->T); 96 | 97 | /* qhasm: return */ 98 | -------------------------------------------------------------------------------- /ed25519-supercop/ref10/ge_add.q: -------------------------------------------------------------------------------- 1 | :name:fe:r->X:r->Y:r->Z:r->T:t0:t1:t2:t3:t4:t5:p->X:p->Y:p->Z:p->T:q->YplusX:q->YminusX:q->Z:q->T2d: 2 | fe r:var/r=fe: 3 | 4 | enter f:enter/f:>X1=fe#11:>Y1=fe#12:>Z1=fe#13:>T1=fe#14:>YpX2=fe#15:>YmX2=fe#16:>Z2=fe#17:>T2d2=fe#18: 5 | return:nofallthrough:h=fe:asm/fe_add(>h,h=fe:asm/fe_sub(>h,h=fe:asm/fe_mul(>h,h=fe:asm/fe_sq(>h,h=fe:asm/fe_add(>h,> 3] >> (i & 7)); 11 | 12 | for (i = 0;i < 256;++i) 13 | if (r[i]) { 14 | for (b = 1;b <= 6 && i + b < 256;++b) { 15 | if (r[i + b]) { 16 | if (r[i] + (r[i + b] << b) <= 15) { 17 | r[i] += r[i + b] << b; r[i + b] = 0; 18 | } else if (r[i] - (r[i + b] << b) >= -15) { 19 | r[i] -= r[i + b] << b; 20 | for (k = i + b;k < 256;++k) { 21 | if (!r[k]) { 22 | r[k] = 1; 23 | break; 24 | } 25 | r[k] = 0; 26 | } 27 | } else 28 | break; 29 | } 30 | } 31 | } 32 | 33 | } 34 | 35 | static ge_precomp Bi[8] = { 36 | #include "base2.h" 37 | } ; 38 | 39 | /* 40 | r = a * A + b * B 41 | where a = a[0]+256*a[1]+...+256^31 a[31]. 42 | and b = b[0]+256*b[1]+...+256^31 b[31]. 43 | B is the Ed25519 base point (x,4/5) with x positive. 44 | */ 45 | 46 | void ge_double_scalarmult_vartime(ge_p2 *r,const unsigned char *a,const ge_p3 *A,const unsigned char *b) 47 | { 48 | signed char aslide[256]; 49 | signed char bslide[256]; 50 | ge_cached Ai[8]; /* A,3A,5A,7A,9A,11A,13A,15A */ 51 | ge_p1p1 t; 52 | ge_p3 u; 53 | ge_p3 A2; 54 | int i; 55 | 56 | slide(aslide,a); 57 | slide(bslide,b); 58 | 59 | ge_p3_to_cached(&Ai[0],A); 60 | ge_p3_dbl(&t,A); ge_p1p1_to_p3(&A2,&t); 61 | ge_add(&t,&A2,&Ai[0]); ge_p1p1_to_p3(&u,&t); ge_p3_to_cached(&Ai[1],&u); 62 | ge_add(&t,&A2,&Ai[1]); ge_p1p1_to_p3(&u,&t); ge_p3_to_cached(&Ai[2],&u); 63 | ge_add(&t,&A2,&Ai[2]); ge_p1p1_to_p3(&u,&t); ge_p3_to_cached(&Ai[3],&u); 64 | ge_add(&t,&A2,&Ai[3]); ge_p1p1_to_p3(&u,&t); ge_p3_to_cached(&Ai[4],&u); 65 | ge_add(&t,&A2,&Ai[4]); ge_p1p1_to_p3(&u,&t); ge_p3_to_cached(&Ai[5],&u); 66 | ge_add(&t,&A2,&Ai[5]); ge_p1p1_to_p3(&u,&t); ge_p3_to_cached(&Ai[6],&u); 67 | ge_add(&t,&A2,&Ai[6]); ge_p1p1_to_p3(&u,&t); ge_p3_to_cached(&Ai[7],&u); 68 | 69 | ge_p2_0(r); 70 | 71 | for (i = 255;i >= 0;--i) { 72 | if (aslide[i] || bslide[i]) break; 73 | } 74 | 75 | for (;i >= 0;--i) { 76 | ge_p2_dbl(&t,r); 77 | 78 | if (aslide[i] > 0) { 79 | ge_p1p1_to_p3(&u,&t); 80 | ge_add(&t,&u,&Ai[aslide[i]/2]); 81 | } else if (aslide[i] < 0) { 82 | ge_p1p1_to_p3(&u,&t); 83 | ge_sub(&t,&u,&Ai[(-aslide[i])/2]); 84 | } 85 | 86 | if (bslide[i] > 0) { 87 | ge_p1p1_to_p3(&u,&t); 88 | ge_madd(&t,&u,&Bi[bslide[i]/2]); 89 | } else if (bslide[i] < 0) { 90 | ge_p1p1_to_p3(&u,&t); 91 | ge_msub(&t,&u,&Bi[(-bslide[i])/2]); 92 | } 93 | 94 | ge_p1p1_to_p2(r,&t); 95 | } 96 | } 97 | -------------------------------------------------------------------------------- /ed25519-supercop/ref10/ge_frombytes.c: -------------------------------------------------------------------------------- 1 | #include "ge.h" 2 | 3 | static const fe d = { 4 | #include "d.h" 5 | } ; 6 | 7 | static const fe sqrtm1 = { 8 | #include "sqrtm1.h" 9 | } ; 10 | 11 | int ge_frombytes_negate_vartime(ge_p3 *h,const unsigned char *s) 12 | { 13 | fe u; 14 | fe v; 15 | fe v3; 16 | fe vxx; 17 | fe check; 18 | 19 | fe_frombytes(h->Y,s); 20 | fe_1(h->Z); 21 | fe_sq(u,h->Y); 22 | fe_mul(v,u,d); 23 | fe_sub(u,u,h->Z); /* u = y^2-1 */ 24 | fe_add(v,v,h->Z); /* v = dy^2+1 */ 25 | 26 | fe_sq(v3,v); 27 | fe_mul(v3,v3,v); /* v3 = v^3 */ 28 | fe_sq(h->X,v3); 29 | fe_mul(h->X,h->X,v); 30 | fe_mul(h->X,h->X,u); /* x = uv^7 */ 31 | 32 | fe_pow22523(h->X,h->X); /* x = (uv^7)^((q-5)/8) */ 33 | fe_mul(h->X,h->X,v3); 34 | fe_mul(h->X,h->X,u); /* x = uv^3(uv^7)^((q-5)/8) */ 35 | 36 | fe_sq(vxx,h->X); 37 | fe_mul(vxx,vxx,v); 38 | fe_sub(check,vxx,u); /* vx^2-u */ 39 | if (fe_isnonzero(check)) { 40 | fe_add(check,vxx,u); /* vx^2+u */ 41 | if (fe_isnonzero(check)) return -1; 42 | fe_mul(h->X,h->X,sqrtm1); 43 | } 44 | 45 | if (fe_isnegative(h->X) == (s[31] >> 7)) 46 | fe_neg(h->X,h->X); 47 | 48 | fe_mul(h->T,h->X,h->Y); 49 | return 0; 50 | } 51 | -------------------------------------------------------------------------------- /ed25519-supercop/ref10/ge_madd.c: -------------------------------------------------------------------------------- 1 | #include "ge.h" 2 | 3 | /* 4 | r = p + q 5 | */ 6 | 7 | void ge_madd(ge_p1p1 *r,const ge_p3 *p,const ge_precomp *q) 8 | { 9 | fe t0; 10 | #include "ge_madd.h" 11 | } 12 | -------------------------------------------------------------------------------- /ed25519-supercop/ref10/ge_madd.h: -------------------------------------------------------------------------------- 1 | 2 | /* qhasm: enter ge_madd */ 3 | 4 | /* qhasm: fe X1 */ 5 | 6 | /* qhasm: fe Y1 */ 7 | 8 | /* qhasm: fe Z1 */ 9 | 10 | /* qhasm: fe T1 */ 11 | 12 | /* qhasm: fe ypx2 */ 13 | 14 | /* qhasm: fe ymx2 */ 15 | 16 | /* qhasm: fe xy2d2 */ 17 | 18 | /* qhasm: fe X3 */ 19 | 20 | /* qhasm: fe Y3 */ 21 | 22 | /* qhasm: fe Z3 */ 23 | 24 | /* qhasm: fe T3 */ 25 | 26 | /* qhasm: fe YpX1 */ 27 | 28 | /* qhasm: fe YmX1 */ 29 | 30 | /* qhasm: fe A */ 31 | 32 | /* qhasm: fe B */ 33 | 34 | /* qhasm: fe C */ 35 | 36 | /* qhasm: fe D */ 37 | 38 | /* qhasm: YpX1 = Y1+X1 */ 39 | /* asm 1: fe_add(>YpX1=fe#1,YpX1=r->X,Y,X); */ 41 | fe_add(r->X,p->Y,p->X); 42 | 43 | /* qhasm: YmX1 = Y1-X1 */ 44 | /* asm 1: fe_sub(>YmX1=fe#2,YmX1=r->Y,Y,X); */ 46 | fe_sub(r->Y,p->Y,p->X); 47 | 48 | /* qhasm: A = YpX1*ypx2 */ 49 | /* asm 1: fe_mul(>A=fe#3,A=r->Z,X,yplusx); */ 51 | fe_mul(r->Z,r->X,q->yplusx); 52 | 53 | /* qhasm: B = YmX1*ymx2 */ 54 | /* asm 1: fe_mul(>B=fe#2,B=r->Y,Y,yminusx); */ 56 | fe_mul(r->Y,r->Y,q->yminusx); 57 | 58 | /* qhasm: C = xy2d2*T1 */ 59 | /* asm 1: fe_mul(>C=fe#4,C=r->T,xy2d,T); */ 61 | fe_mul(r->T,q->xy2d,p->T); 62 | 63 | /* qhasm: D = 2*Z1 */ 64 | /* asm 1: fe_add(>D=fe#5,D=t0,Z,Z); */ 66 | fe_add(t0,p->Z,p->Z); 67 | 68 | /* qhasm: X3 = A-B */ 69 | /* asm 1: fe_sub(>X3=fe#1,X3=r->X,Z,Y); */ 71 | fe_sub(r->X,r->Z,r->Y); 72 | 73 | /* qhasm: Y3 = A+B */ 74 | /* asm 1: fe_add(>Y3=fe#2,Y3=r->Y,Z,Y); */ 76 | fe_add(r->Y,r->Z,r->Y); 77 | 78 | /* qhasm: Z3 = D+C */ 79 | /* asm 1: fe_add(>Z3=fe#3,Z3=r->Z,T); */ 81 | fe_add(r->Z,t0,r->T); 82 | 83 | /* qhasm: T3 = D-C */ 84 | /* asm 1: fe_sub(>T3=fe#4,T3=r->T,T); */ 86 | fe_sub(r->T,t0,r->T); 87 | 88 | /* qhasm: return */ 89 | -------------------------------------------------------------------------------- /ed25519-supercop/ref10/ge_madd.q: -------------------------------------------------------------------------------- 1 | :name:fe:r->X:r->Y:r->Z:r->T:t0:t1:t2:t3:t4:t5:p->X:p->Y:p->Z:p->T:q->yplusx:q->yminusx:q->xy2d: 2 | fe r:var/r=fe: 3 | 4 | enter f:enter/f:>X1=fe#11:>Y1=fe#12:>Z1=fe#13:>T1=fe#14:>ypx2=fe#15:>ymx2=fe#16:>xy2d2=fe#17: 5 | return:nofallthrough:h=fe:asm/fe_add(>h,h=fe:asm/fe_sub(>h,h=fe:asm/fe_mul(>h,h=fe:asm/fe_sq(>h,h=fe:asm/fe_add(>h,YpX1=fe#1,YpX1=r->X,Y,X); */ 41 | fe_add(r->X,p->Y,p->X); 42 | 43 | /* qhasm: YmX1 = Y1-X1 */ 44 | /* asm 1: fe_sub(>YmX1=fe#2,YmX1=r->Y,Y,X); */ 46 | fe_sub(r->Y,p->Y,p->X); 47 | 48 | /* qhasm: A = YpX1*ymx2 */ 49 | /* asm 1: fe_mul(>A=fe#3,A=r->Z,X,yminusx); */ 51 | fe_mul(r->Z,r->X,q->yminusx); 52 | 53 | /* qhasm: B = YmX1*ypx2 */ 54 | /* asm 1: fe_mul(>B=fe#2,B=r->Y,Y,yplusx); */ 56 | fe_mul(r->Y,r->Y,q->yplusx); 57 | 58 | /* qhasm: C = xy2d2*T1 */ 59 | /* asm 1: fe_mul(>C=fe#4,C=r->T,xy2d,T); */ 61 | fe_mul(r->T,q->xy2d,p->T); 62 | 63 | /* qhasm: D = 2*Z1 */ 64 | /* asm 1: fe_add(>D=fe#5,D=t0,Z,Z); */ 66 | fe_add(t0,p->Z,p->Z); 67 | 68 | /* qhasm: X3 = A-B */ 69 | /* asm 1: fe_sub(>X3=fe#1,X3=r->X,Z,Y); */ 71 | fe_sub(r->X,r->Z,r->Y); 72 | 73 | /* qhasm: Y3 = A+B */ 74 | /* asm 1: fe_add(>Y3=fe#2,Y3=r->Y,Z,Y); */ 76 | fe_add(r->Y,r->Z,r->Y); 77 | 78 | /* qhasm: Z3 = D-C */ 79 | /* asm 1: fe_sub(>Z3=fe#3,Z3=r->Z,T); */ 81 | fe_sub(r->Z,t0,r->T); 82 | 83 | /* qhasm: T3 = D+C */ 84 | /* asm 1: fe_add(>T3=fe#4,T3=r->T,T); */ 86 | fe_add(r->T,t0,r->T); 87 | 88 | /* qhasm: return */ 89 | -------------------------------------------------------------------------------- /ed25519-supercop/ref10/ge_msub.q: -------------------------------------------------------------------------------- 1 | :name:fe:r->X:r->Y:r->Z:r->T:t0:t1:t2:t3:t4:t5:p->X:p->Y:p->Z:p->T:q->yplusx:q->yminusx:q->xy2d: 2 | fe r:var/r=fe: 3 | 4 | enter f:enter/f:>X1=fe#11:>Y1=fe#12:>Z1=fe#13:>T1=fe#14:>ypx2=fe#15:>ymx2=fe#16:>xy2d2=fe#17: 5 | return:nofallthrough:h=fe:asm/fe_add(>h,h=fe:asm/fe_sub(>h,h=fe:asm/fe_mul(>h,h=fe:asm/fe_sq(>h,h=fe:asm/fe_add(>h,X,p->X,p->T); 10 | fe_mul(r->Y,p->Y,p->Z); 11 | fe_mul(r->Z,p->Z,p->T); 12 | } 13 | -------------------------------------------------------------------------------- /ed25519-supercop/ref10/ge_p1p1_to_p3.c: -------------------------------------------------------------------------------- 1 | #include "ge.h" 2 | 3 | /* 4 | r = p 5 | */ 6 | 7 | extern void ge_p1p1_to_p3(ge_p3 *r,const ge_p1p1 *p) 8 | { 9 | fe_mul(r->X,p->X,p->T); 10 | fe_mul(r->Y,p->Y,p->Z); 11 | fe_mul(r->Z,p->Z,p->T); 12 | fe_mul(r->T,p->X,p->Y); 13 | } 14 | -------------------------------------------------------------------------------- /ed25519-supercop/ref10/ge_p2_0.c: -------------------------------------------------------------------------------- 1 | #include "ge.h" 2 | 3 | void ge_p2_0(ge_p2 *h) 4 | { 5 | fe_0(h->X); 6 | fe_1(h->Y); 7 | fe_1(h->Z); 8 | } 9 | -------------------------------------------------------------------------------- /ed25519-supercop/ref10/ge_p2_dbl.c: -------------------------------------------------------------------------------- 1 | #include "ge.h" 2 | 3 | /* 4 | r = 2 * p 5 | */ 6 | 7 | void ge_p2_dbl(ge_p1p1 *r,const ge_p2 *p) 8 | { 9 | fe t0; 10 | #include "ge_p2_dbl.h" 11 | } 12 | -------------------------------------------------------------------------------- /ed25519-supercop/ref10/ge_p2_dbl.h: -------------------------------------------------------------------------------- 1 | 2 | /* qhasm: enter ge_p2_dbl */ 3 | 4 | /* qhasm: fe X1 */ 5 | 6 | /* qhasm: fe Y1 */ 7 | 8 | /* qhasm: fe Z1 */ 9 | 10 | /* qhasm: fe A */ 11 | 12 | /* qhasm: fe AA */ 13 | 14 | /* qhasm: fe XX */ 15 | 16 | /* qhasm: fe YY */ 17 | 18 | /* qhasm: fe B */ 19 | 20 | /* qhasm: fe X3 */ 21 | 22 | /* qhasm: fe Y3 */ 23 | 24 | /* qhasm: fe Z3 */ 25 | 26 | /* qhasm: fe T3 */ 27 | 28 | /* qhasm: XX=X1^2 */ 29 | /* asm 1: fe_sq(>XX=fe#1,XX=r->X,X); */ 31 | fe_sq(r->X,p->X); 32 | 33 | /* qhasm: YY=Y1^2 */ 34 | /* asm 1: fe_sq(>YY=fe#3,YY=r->Z,Y); */ 36 | fe_sq(r->Z,p->Y); 37 | 38 | /* qhasm: B=2*Z1^2 */ 39 | /* asm 1: fe_sq2(>B=fe#4,B=r->T,Z); */ 41 | fe_sq2(r->T,p->Z); 42 | 43 | /* qhasm: A=X1+Y1 */ 44 | /* asm 1: fe_add(>A=fe#2,A=r->Y,X,Y); */ 46 | fe_add(r->Y,p->X,p->Y); 47 | 48 | /* qhasm: AA=A^2 */ 49 | /* asm 1: fe_sq(>AA=fe#5,AA=t0,Y); */ 51 | fe_sq(t0,r->Y); 52 | 53 | /* qhasm: Y3=YY+XX */ 54 | /* asm 1: fe_add(>Y3=fe#2,Y3=r->Y,Z,X); */ 56 | fe_add(r->Y,r->Z,r->X); 57 | 58 | /* qhasm: Z3=YY-XX */ 59 | /* asm 1: fe_sub(>Z3=fe#3,Z3=r->Z,Z,X); */ 61 | fe_sub(r->Z,r->Z,r->X); 62 | 63 | /* qhasm: X3=AA-Y3 */ 64 | /* asm 1: fe_sub(>X3=fe#1,X3=r->X,Y); */ 66 | fe_sub(r->X,t0,r->Y); 67 | 68 | /* qhasm: T3=B-Z3 */ 69 | /* asm 1: fe_sub(>T3=fe#4,T3=r->T,T,Z); */ 71 | fe_sub(r->T,r->T,r->Z); 72 | 73 | /* qhasm: return */ 74 | -------------------------------------------------------------------------------- /ed25519-supercop/ref10/ge_p2_dbl.q: -------------------------------------------------------------------------------- 1 | :name:fe:r->X:r->Y:r->Z:r->T:t0:t1:t2:t3:t4:t5:p->X:p->Y:p->Z: 2 | fe r:var/r=fe: 3 | 4 | enter f:enter/f:>X1=fe#11:>Y1=fe#12:>Z1=fe#13: 5 | return:nofallthrough:h=fe:asm/fe_add(>h,h=fe:asm/fe_sub(>h,h=fe:asm/fe_mul(>h,h=fe:asm/fe_sq(>h,h=fe:asm/fe_sq2(>h,h=fe:asm/fe_add(>h,X); 6 | fe_1(h->Y); 7 | fe_1(h->Z); 8 | fe_0(h->T); 9 | } 10 | -------------------------------------------------------------------------------- /ed25519-supercop/ref10/ge_p3_dbl.c: -------------------------------------------------------------------------------- 1 | #include "ge.h" 2 | 3 | /* 4 | r = 2 * p 5 | */ 6 | 7 | void ge_p3_dbl(ge_p1p1 *r,const ge_p3 *p) 8 | { 9 | ge_p2 q; 10 | ge_p3_to_p2(&q,p); 11 | ge_p2_dbl(r,&q); 12 | } 13 | -------------------------------------------------------------------------------- /ed25519-supercop/ref10/ge_p3_to_cached.c: -------------------------------------------------------------------------------- 1 | #include "ge.h" 2 | 3 | /* 4 | r = p 5 | */ 6 | 7 | static const fe d2 = { 8 | #include "d2.h" 9 | } ; 10 | 11 | extern void ge_p3_to_cached(ge_cached *r,const ge_p3 *p) 12 | { 13 | fe_add(r->YplusX,p->Y,p->X); 14 | fe_sub(r->YminusX,p->Y,p->X); 15 | fe_copy(r->Z,p->Z); 16 | fe_mul(r->T2d,p->T,d2); 17 | } 18 | -------------------------------------------------------------------------------- /ed25519-supercop/ref10/ge_p3_to_p2.c: -------------------------------------------------------------------------------- 1 | #include "ge.h" 2 | 3 | /* 4 | r = p 5 | */ 6 | 7 | extern void ge_p3_to_p2(ge_p2 *r,const ge_p3 *p) 8 | { 9 | fe_copy(r->X,p->X); 10 | fe_copy(r->Y,p->Y); 11 | fe_copy(r->Z,p->Z); 12 | } 13 | -------------------------------------------------------------------------------- /ed25519-supercop/ref10/ge_p3_tobytes.c: -------------------------------------------------------------------------------- 1 | #include "ge.h" 2 | 3 | void ge_p3_tobytes(unsigned char *s,const ge_p3 *h) 4 | { 5 | fe recip; 6 | fe x; 7 | fe y; 8 | 9 | fe_invert(recip,h->Z); 10 | fe_mul(x,h->X,recip); 11 | fe_mul(y,h->Y,recip); 12 | fe_tobytes(s,y); 13 | s[31] ^= fe_isnegative(x) << 7; 14 | } 15 | -------------------------------------------------------------------------------- /ed25519-supercop/ref10/ge_precomp_0.c: -------------------------------------------------------------------------------- 1 | #include "ge.h" 2 | 3 | void ge_precomp_0(ge_precomp *h) 4 | { 5 | fe_1(h->yplusx); 6 | fe_1(h->yminusx); 7 | fe_0(h->xy2d); 8 | } 9 | -------------------------------------------------------------------------------- /ed25519-supercop/ref10/ge_scalarmult_base.c: -------------------------------------------------------------------------------- 1 | #include "ge.h" 2 | #include "crypto_uint32.h" 3 | 4 | static unsigned char equal(signed char b,signed char c) 5 | { 6 | unsigned char ub = b; 7 | unsigned char uc = c; 8 | unsigned char x = ub ^ uc; /* 0: yes; 1..255: no */ 9 | crypto_uint32 y = x; /* 0: yes; 1..255: no */ 10 | y -= 1; /* 4294967295: yes; 0..254: no */ 11 | y >>= 31; /* 1: yes; 0: no */ 12 | return y; 13 | } 14 | 15 | static unsigned char negative(signed char b) 16 | { 17 | unsigned long long x = b; /* 18446744073709551361..18446744073709551615: yes; 0..255: no */ 18 | x >>= 63; /* 1: yes; 0: no */ 19 | return x; 20 | } 21 | 22 | static void cmov(ge_precomp *t,ge_precomp *u,unsigned char b) 23 | { 24 | fe_cmov(t->yplusx,u->yplusx,b); 25 | fe_cmov(t->yminusx,u->yminusx,b); 26 | fe_cmov(t->xy2d,u->xy2d,b); 27 | } 28 | 29 | /* base[i][j] = (j+1)*256^i*B */ 30 | static ge_precomp base[32][8] = { 31 | #include "base.h" 32 | } ; 33 | 34 | static void select(ge_precomp *t,int pos,signed char b) 35 | { 36 | ge_precomp minust; 37 | unsigned char bnegative = negative(b); 38 | unsigned char babs = b - (((-bnegative) & b) << 1); 39 | 40 | ge_precomp_0(t); 41 | cmov(t,&base[pos][0],equal(babs,1)); 42 | cmov(t,&base[pos][1],equal(babs,2)); 43 | cmov(t,&base[pos][2],equal(babs,3)); 44 | cmov(t,&base[pos][3],equal(babs,4)); 45 | cmov(t,&base[pos][4],equal(babs,5)); 46 | cmov(t,&base[pos][5],equal(babs,6)); 47 | cmov(t,&base[pos][6],equal(babs,7)); 48 | cmov(t,&base[pos][7],equal(babs,8)); 49 | fe_copy(minust.yplusx,t->yminusx); 50 | fe_copy(minust.yminusx,t->yplusx); 51 | fe_neg(minust.xy2d,t->xy2d); 52 | cmov(t,&minust,bnegative); 53 | } 54 | 55 | /* 56 | h = a * B 57 | where a = a[0]+256*a[1]+...+256^31 a[31] 58 | B is the Ed25519 base point (x,4/5) with x positive. 59 | 60 | Preconditions: 61 | a[31] <= 127 62 | */ 63 | 64 | void ge_scalarmult_base(ge_p3 *h,const unsigned char *a) 65 | { 66 | signed char e[64]; 67 | signed char carry; 68 | ge_p1p1 r; 69 | ge_p2 s; 70 | ge_precomp t; 71 | int i; 72 | 73 | for (i = 0;i < 32;++i) { 74 | e[2 * i + 0] = (a[i] >> 0) & 15; 75 | e[2 * i + 1] = (a[i] >> 4) & 15; 76 | } 77 | /* each e[i] is between 0 and 15 */ 78 | /* e[63] is between 0 and 7 */ 79 | 80 | carry = 0; 81 | for (i = 0;i < 63;++i) { 82 | e[i] += carry; 83 | carry = e[i] + 8; 84 | carry >>= 4; 85 | e[i] -= carry << 4; 86 | } 87 | e[63] += carry; 88 | /* each e[i] is between -8 and 8 */ 89 | 90 | ge_p3_0(h); 91 | for (i = 1;i < 64;i += 2) { 92 | select(&t,i / 2,e[i]); 93 | ge_madd(&r,h,&t); ge_p1p1_to_p3(h,&r); 94 | } 95 | 96 | ge_p3_dbl(&r,h); ge_p1p1_to_p2(&s,&r); 97 | ge_p2_dbl(&r,&s); ge_p1p1_to_p2(&s,&r); 98 | ge_p2_dbl(&r,&s); ge_p1p1_to_p2(&s,&r); 99 | ge_p2_dbl(&r,&s); ge_p1p1_to_p3(h,&r); 100 | 101 | for (i = 0;i < 64;i += 2) { 102 | select(&t,i / 2,e[i]); 103 | ge_madd(&r,h,&t); ge_p1p1_to_p3(h,&r); 104 | } 105 | } 106 | -------------------------------------------------------------------------------- /ed25519-supercop/ref10/ge_sub.c: -------------------------------------------------------------------------------- 1 | #include "ge.h" 2 | 3 | /* 4 | r = p - q 5 | */ 6 | 7 | void ge_sub(ge_p1p1 *r,const ge_p3 *p,const ge_cached *q) 8 | { 9 | fe t0; 10 | #include "ge_sub.h" 11 | } 12 | -------------------------------------------------------------------------------- /ed25519-supercop/ref10/ge_sub.h: -------------------------------------------------------------------------------- 1 | 2 | /* qhasm: enter ge_sub */ 3 | 4 | /* qhasm: fe X1 */ 5 | 6 | /* qhasm: fe Y1 */ 7 | 8 | /* qhasm: fe Z1 */ 9 | 10 | /* qhasm: fe Z2 */ 11 | 12 | /* qhasm: fe T1 */ 13 | 14 | /* qhasm: fe ZZ */ 15 | 16 | /* qhasm: fe YpX2 */ 17 | 18 | /* qhasm: fe YmX2 */ 19 | 20 | /* qhasm: fe T2d2 */ 21 | 22 | /* qhasm: fe X3 */ 23 | 24 | /* qhasm: fe Y3 */ 25 | 26 | /* qhasm: fe Z3 */ 27 | 28 | /* qhasm: fe T3 */ 29 | 30 | /* qhasm: fe YpX1 */ 31 | 32 | /* qhasm: fe YmX1 */ 33 | 34 | /* qhasm: fe A */ 35 | 36 | /* qhasm: fe B */ 37 | 38 | /* qhasm: fe C */ 39 | 40 | /* qhasm: fe D */ 41 | 42 | /* qhasm: YpX1 = Y1+X1 */ 43 | /* asm 1: fe_add(>YpX1=fe#1,YpX1=r->X,Y,X); */ 45 | fe_add(r->X,p->Y,p->X); 46 | 47 | /* qhasm: YmX1 = Y1-X1 */ 48 | /* asm 1: fe_sub(>YmX1=fe#2,YmX1=r->Y,Y,X); */ 50 | fe_sub(r->Y,p->Y,p->X); 51 | 52 | /* qhasm: A = YpX1*YmX2 */ 53 | /* asm 1: fe_mul(>A=fe#3,A=r->Z,X,YminusX); */ 55 | fe_mul(r->Z,r->X,q->YminusX); 56 | 57 | /* qhasm: B = YmX1*YpX2 */ 58 | /* asm 1: fe_mul(>B=fe#2,B=r->Y,Y,YplusX); */ 60 | fe_mul(r->Y,r->Y,q->YplusX); 61 | 62 | /* qhasm: C = T2d2*T1 */ 63 | /* asm 1: fe_mul(>C=fe#4,C=r->T,T2d,T); */ 65 | fe_mul(r->T,q->T2d,p->T); 66 | 67 | /* qhasm: ZZ = Z1*Z2 */ 68 | /* asm 1: fe_mul(>ZZ=fe#1,ZZ=r->X,Z,Z); */ 70 | fe_mul(r->X,p->Z,q->Z); 71 | 72 | /* qhasm: D = 2*ZZ */ 73 | /* asm 1: fe_add(>D=fe#5,D=t0,X,X); */ 75 | fe_add(t0,r->X,r->X); 76 | 77 | /* qhasm: X3 = A-B */ 78 | /* asm 1: fe_sub(>X3=fe#1,X3=r->X,Z,Y); */ 80 | fe_sub(r->X,r->Z,r->Y); 81 | 82 | /* qhasm: Y3 = A+B */ 83 | /* asm 1: fe_add(>Y3=fe#2,Y3=r->Y,Z,Y); */ 85 | fe_add(r->Y,r->Z,r->Y); 86 | 87 | /* qhasm: Z3 = D-C */ 88 | /* asm 1: fe_sub(>Z3=fe#3,Z3=r->Z,T); */ 90 | fe_sub(r->Z,t0,r->T); 91 | 92 | /* qhasm: T3 = D+C */ 93 | /* asm 1: fe_add(>T3=fe#4,T3=r->T,T); */ 95 | fe_add(r->T,t0,r->T); 96 | 97 | /* qhasm: return */ 98 | -------------------------------------------------------------------------------- /ed25519-supercop/ref10/ge_sub.q: -------------------------------------------------------------------------------- 1 | :name:fe:r->X:r->Y:r->Z:r->T:t0:t1:t2:t3:t4:t5:p->X:p->Y:p->Z:p->T:q->YplusX:q->YminusX:q->Z:q->T2d: 2 | fe r:var/r=fe: 3 | 4 | enter f:enter/f:>X1=fe#11:>Y1=fe#12:>Z1=fe#13:>T1=fe#14:>YpX2=fe#15:>YmX2=fe#16:>Z2=fe#17:>T2d2=fe#18: 5 | return:nofallthrough:h=fe:asm/fe_add(>h,h=fe:asm/fe_sub(>h,h=fe:asm/fe_mul(>h,h=fe:asm/fe_sq(>h,h=fe:asm/fe_add(>h,Z); 10 | fe_mul(x,h->X,recip); 11 | fe_mul(y,h->Y,recip); 12 | fe_tobytes(s,y); 13 | s[31] ^= fe_isnegative(x) << 7; 14 | } 15 | -------------------------------------------------------------------------------- /ed25519-supercop/ref10/keypair.c: -------------------------------------------------------------------------------- 1 | #include 2 | #include "randombytes.h" 3 | #include "crypto_sign.h" 4 | #include "crypto_hash_sha512.h" 5 | #include "ge.h" 6 | 7 | int crypto_sign_keypair(unsigned char *pk,unsigned char *sk) 8 | { 9 | unsigned char az[64]; 10 | ge_p3 A; 11 | 12 | randombytes(sk,32); 13 | crypto_hash_sha512(az,sk,32); 14 | az[0] &= 248; 15 | az[31] &= 63; 16 | az[31] |= 64; 17 | 18 | ge_scalarmult_base(&A,az); 19 | ge_p3_tobytes(pk,&A); 20 | 21 | memmove(sk + 32,pk,32); 22 | return 0; 23 | } 24 | -------------------------------------------------------------------------------- /ed25519-supercop/ref10/open.c: -------------------------------------------------------------------------------- 1 | #include 2 | #include "crypto_sign.h" 3 | #include "crypto_hash_sha512.h" 4 | #include "crypto_verify_32.h" 5 | #include "ge.h" 6 | #include "sc.h" 7 | 8 | int crypto_sign_open( 9 | unsigned char *m,unsigned long long *mlen, 10 | const unsigned char *sm,unsigned long long smlen, 11 | const unsigned char *pk 12 | ) 13 | { 14 | unsigned char pkcopy[32]; 15 | unsigned char rcopy[32]; 16 | unsigned char scopy[32]; 17 | unsigned char h[64]; 18 | unsigned char rcheck[32]; 19 | ge_p3 A; 20 | ge_p2 R; 21 | 22 | if (smlen < 64) goto badsig; 23 | if (sm[63] & 224) goto badsig; 24 | if (ge_frombytes_negate_vartime(&A,pk) != 0) goto badsig; 25 | 26 | memmove(pkcopy,pk,32); 27 | memmove(rcopy,sm,32); 28 | memmove(scopy,sm + 32,32); 29 | 30 | memmove(m,sm,smlen); 31 | memmove(m + 32,pkcopy,32); 32 | crypto_hash_sha512(h,m,smlen); 33 | sc_reduce(h); 34 | 35 | ge_double_scalarmult_vartime(&R,h,&A,scopy); 36 | ge_tobytes(rcheck,&R); 37 | if (crypto_verify_32(rcheck,rcopy) == 0) { 38 | memmove(m,m + 64,smlen - 64); 39 | memset(m + smlen - 64,0,64); 40 | *mlen = smlen - 64; 41 | return 0; 42 | } 43 | 44 | badsig: 45 | *mlen = -1; 46 | memset(m,0,smlen); 47 | return -1; 48 | } 49 | -------------------------------------------------------------------------------- /ed25519-supercop/ref10/pow22523.q: -------------------------------------------------------------------------------- 1 | :name:fe:t0:t1:t2:t3:t4:t5:t6:t7:t8:t9:z:out: 2 | fe r:var/r=fe: 3 | 4 | enter f:enter/f:>z1=fe#11: 5 | return:nofallthrough:h=fe:asm/fe_mul(>h,h=fe:#k:asm/fe_sq(>h,h,>h);: 9 | 10 | : 11 | 12 | fe z1 13 | fe z2 14 | fe z8 15 | fe z9 16 | fe z11 17 | fe z22 18 | fe z_5_0 19 | fe z_10_5 20 | fe z_10_0 21 | fe z_20_10 22 | fe z_20_0 23 | fe z_40_20 24 | fe z_40_0 25 | fe z_50_10 26 | fe z_50_0 27 | fe z_100_50 28 | fe z_100_0 29 | fe z_200_100 30 | fe z_200_0 31 | fe z_250_50 32 | fe z_250_0 33 | fe z_252_2 34 | fe z_252_3 35 | 36 | enter pow22523 37 | 38 | z2 = z1^2^1 39 | z8 = z2^2^2 40 | z9 = z1*z8 41 | z11 = z2*z9 42 | z22 = z11^2^1 43 | z_5_0 = z9*z22 44 | z_10_5 = z_5_0^2^5 45 | z_10_0 = z_10_5*z_5_0 46 | z_20_10 = z_10_0^2^10 47 | z_20_0 = z_20_10*z_10_0 48 | z_40_20 = z_20_0^2^20 49 | z_40_0 = z_40_20*z_20_0 50 | z_50_10 = z_40_0^2^10 51 | z_50_0 = z_50_10*z_10_0 52 | z_100_50 = z_50_0^2^50 53 | z_100_0 = z_100_50*z_50_0 54 | z_200_100 = z_100_0^2^100 55 | z_200_0 = z_200_100*z_100_0 56 | z_250_50 = z_200_0^2^50 57 | z_250_0 = z_250_50*z_50_0 58 | z_252_2 = z_250_0^2^2 59 | z_252_3 = z_252_2*z1 60 | 61 | return 62 | -------------------------------------------------------------------------------- /ed25519-supercop/ref10/pow225521.q: -------------------------------------------------------------------------------- 1 | :name:fe:t0:t1:t2:t3:t4:t5:t6:t7:t8:t9:z:out: 2 | fe r:var/r=fe: 3 | 4 | enter f:enter/f:>z1=fe#11: 5 | return:nofallthrough:h=fe:asm/fe_mul(>h,h=fe:#k:asm/fe_sq(>h,h,>h);: 9 | 10 | : 11 | 12 | fe z1 13 | fe z2 14 | fe z8 15 | fe z9 16 | fe z11 17 | fe z22 18 | fe z_5_0 19 | fe z_10_5 20 | fe z_10_0 21 | fe z_20_10 22 | fe z_20_0 23 | fe z_40_20 24 | fe z_40_0 25 | fe z_50_10 26 | fe z_50_0 27 | fe z_100_50 28 | fe z_100_0 29 | fe z_200_100 30 | fe z_200_0 31 | fe z_250_50 32 | fe z_250_0 33 | fe z_255_5 34 | fe z_255_21 35 | 36 | enter pow225521 37 | 38 | z2 = z1^2^1 39 | z8 = z2^2^2 40 | z9 = z1*z8 41 | z11 = z2*z9 42 | z22 = z11^2^1 43 | z_5_0 = z9*z22 44 | z_10_5 = z_5_0^2^5 45 | z_10_0 = z_10_5*z_5_0 46 | z_20_10 = z_10_0^2^10 47 | z_20_0 = z_20_10*z_10_0 48 | z_40_20 = z_20_0^2^20 49 | z_40_0 = z_40_20*z_20_0 50 | z_50_10 = z_40_0^2^10 51 | z_50_0 = z_50_10*z_10_0 52 | z_100_50 = z_50_0^2^50 53 | z_100_0 = z_100_50*z_50_0 54 | z_200_100 = z_100_0^2^100 55 | z_200_0 = z_200_100*z_100_0 56 | z_250_50 = z_200_0^2^50 57 | z_250_0 = z_250_50*z_50_0 58 | z_255_5 = z_250_0^2^5 59 | z_255_21 = z_255_5*z11 60 | 61 | return 62 | -------------------------------------------------------------------------------- /ed25519-supercop/ref10/q2h.sh: -------------------------------------------------------------------------------- 1 | #!/bin/sh 2 | sed 's/^#.*//' \ 3 | | qhasm-generic \ 4 | | sed 's_//\(.*\)$_/*\1 */_' 5 | -------------------------------------------------------------------------------- /ed25519-supercop/ref10/sc.h: -------------------------------------------------------------------------------- 1 | #ifndef SC_H 2 | #define SC_H 3 | 4 | /* 5 | The set of scalars is \Z/l 6 | where l = 2^252 + 27742317777372353535851937790883648493. 7 | */ 8 | 9 | #define sc_reduce crypto_sign_ed25519_ref10_sc_reduce 10 | #define sc_muladd crypto_sign_ed25519_ref10_sc_muladd 11 | 12 | extern void sc_reduce(unsigned char *); 13 | extern void sc_muladd(unsigned char *,const unsigned char *,const unsigned char *,const unsigned char *); 14 | 15 | #endif 16 | -------------------------------------------------------------------------------- /ed25519-supercop/ref10/sign.c: -------------------------------------------------------------------------------- 1 | #include 2 | #include "crypto_sign.h" 3 | #include "crypto_hash_sha512.h" 4 | #include "ge.h" 5 | #include "sc.h" 6 | 7 | int crypto_sign( 8 | unsigned char *sm,unsigned long long *smlen, 9 | const unsigned char *m,unsigned long long mlen, 10 | const unsigned char *sk 11 | ) 12 | { 13 | unsigned char pk[32]; 14 | unsigned char az[64]; 15 | unsigned char nonce[64]; 16 | unsigned char hram[64]; 17 | ge_p3 R; 18 | 19 | memmove(pk,sk + 32,32); 20 | 21 | crypto_hash_sha512(az,sk,32); 22 | az[0] &= 248; 23 | az[31] &= 63; 24 | az[31] |= 64; 25 | 26 | *smlen = mlen + 64; 27 | memmove(sm + 64,m,mlen); 28 | memmove(sm + 32,az + 32,32); 29 | crypto_hash_sha512(nonce,sm + 32,mlen + 32); 30 | memmove(sm + 32,pk,32); 31 | 32 | sc_reduce(nonce); 33 | ge_scalarmult_base(&R,nonce); 34 | ge_p3_tobytes(sm,&R); 35 | 36 | crypto_hash_sha512(hram,sm,mlen + 64); 37 | sc_reduce(hram); 38 | sc_muladd(sm + 32,hram,az,nonce); 39 | 40 | return 0; 41 | } 42 | -------------------------------------------------------------------------------- /ed25519-supercop/ref10/sqrtm1.h: -------------------------------------------------------------------------------- 1 | -32595792,-7943725,9377950,3500415,12389472,-272473,-25146209,-2005654,326686,11406482 2 | -------------------------------------------------------------------------------- /ed25519-supercop/ref10/sqrtm1.py: -------------------------------------------------------------------------------- 1 | q = 2**255 - 19 2 | 3 | def expmod(b,e,m): 4 | if e == 0: return 1 5 | t = expmod(b,e/2,m)**2 % m 6 | if e & 1: t = (t*b) % m 7 | return t 8 | 9 | def inv(x): 10 | return expmod(x,q-2,q) 11 | 12 | def radix255(x): 13 | x = x % q 14 | if x + x > q: x -= q 15 | x = [x,0,0,0,0,0,0,0,0,0] 16 | bits = [26,25,26,25,26,25,26,25,26,25] 17 | for i in range(9): 18 | carry = (x[i] + 2**(bits[i]-1)) / 2**bits[i] 19 | x[i] -= carry * 2**bits[i] 20 | x[i + 1] += carry 21 | result = "" 22 | for i in range(9): 23 | result = result+str(x[i])+"," 24 | result = result+str(x[9]) 25 | return result 26 | 27 | I = expmod(2,(q-1)/4,q) 28 | print radix255(I) 29 | --------------------------------------------------------------------------------