diff --git a/Cargo.lock b/Cargo.lock index 4b9c613b..7376e456 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -70,7 +70,7 @@ name = "backtrace-sys" version = "0.1.28" source = "registry+https://github.com/rust-lang/crates.io-index" dependencies = [ - "cc 1.0.31 (registry+https://github.com/rust-lang/crates.io-index)", + "cc 1.0.32 (registry+https://github.com/rust-lang/crates.io-index)", "libc 0.2.50 (registry+https://github.com/rust-lang/crates.io-index)", ] @@ -149,7 +149,7 @@ dependencies = [ [[package]] name = "cc" -version = "1.0.31" +version = "1.0.32" source = "registry+https://github.com/rust-lang/crates.io-index" dependencies = [ "rayon 1.0.3 (registry+https://github.com/rust-lang/crates.io-index)", @@ -184,10 +184,10 @@ dependencies = [ [[package]] name = "cmake" -version = "0.1.35" +version = "0.1.37" source = "registry+https://github.com/rust-lang/crates.io-index" dependencies = [ - "cc 1.0.31 (registry+https://github.com/rust-lang/crates.io-index)", + "cc 1.0.32 (registry+https://github.com/rust-lang/crates.io-index)", ] [[package]] @@ -295,6 +295,11 @@ dependencies = [ "lazy_static 1.3.0 (registry+https://github.com/rust-lang/crates.io-index)", ] +[[package]] +name = "crunchy" +version = "0.1.6" +source = "registry+https://github.com/rust-lang/crates.io-index" + [[package]] name = "csv" version = "1.0.5" @@ -317,10 +322,10 @@ name = "curl-sys" version = "0.4.17" source = "registry+https://github.com/rust-lang/crates.io-index" dependencies = [ - "cc 1.0.31 (registry+https://github.com/rust-lang/crates.io-index)", + "cc 1.0.32 (registry+https://github.com/rust-lang/crates.io-index)", "libc 0.2.50 (registry+https://github.com/rust-lang/crates.io-index)", "libz-sys 1.0.25 (registry+https://github.com/rust-lang/crates.io-index)", - "openssl-sys 0.9.42 (registry+https://github.com/rust-lang/crates.io-index)", + "openssl-sys 0.9.43 (registry+https://github.com/rust-lang/crates.io-index)", "pkg-config 0.3.14 (registry+https://github.com/rust-lang/crates.io-index)", "vcpkg 0.2.6 (registry+https://github.com/rust-lang/crates.io-index)", "winapi 0.3.6 (registry+https://github.com/rust-lang/crates.io-index)", @@ -331,6 +336,14 @@ name = "difference" version = "1.0.0" source = "registry+https://github.com/rust-lang/crates.io-index" +[[package]] +name = "digest" +version = "0.7.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +dependencies = [ + "generic-array 0.9.0 (registry+https://github.com/rust-lang/crates.io-index)", +] + [[package]] name = "either" version = "1.5.1" @@ -400,6 +413,14 @@ dependencies = [ "num_cpus 1.10.0 (registry+https://github.com/rust-lang/crates.io-index)", ] +[[package]] +name = "generic-array" +version = "0.9.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +dependencies = [ + "typenum 1.10.0 (registry+https://github.com/rust-lang/crates.io-index)", +] + [[package]] name = "git2" version = "0.8.0" @@ -410,7 +431,7 @@ dependencies = [ "libgit2-sys 0.7.11 (registry+https://github.com/rust-lang/crates.io-index)", "log 0.4.6 (registry+https://github.com/rust-lang/crates.io-index)", "openssl-probe 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)", - "openssl-sys 0.9.42 (registry+https://github.com/rust-lang/crates.io-index)", + "openssl-sys 0.9.43 (registry+https://github.com/rust-lang/crates.io-index)", "url 1.7.2 (registry+https://github.com/rust-lang/crates.io-index)", ] @@ -464,12 +485,12 @@ name = "libgit2-sys" version = "0.7.11" source = "registry+https://github.com/rust-lang/crates.io-index" dependencies = [ - "cc 1.0.31 (registry+https://github.com/rust-lang/crates.io-index)", + "cc 1.0.32 (registry+https://github.com/rust-lang/crates.io-index)", "curl-sys 0.4.17 (registry+https://github.com/rust-lang/crates.io-index)", "libc 0.2.50 (registry+https://github.com/rust-lang/crates.io-index)", "libssh2-sys 0.2.11 (registry+https://github.com/rust-lang/crates.io-index)", "libz-sys 1.0.25 (registry+https://github.com/rust-lang/crates.io-index)", - "openssl-sys 0.9.42 (registry+https://github.com/rust-lang/crates.io-index)", + "openssl-sys 0.9.43 (registry+https://github.com/rust-lang/crates.io-index)", "pkg-config 0.3.14 (registry+https://github.com/rust-lang/crates.io-index)", ] @@ -478,10 +499,10 @@ name = "libssh2-sys" version = "0.2.11" source = "registry+https://github.com/rust-lang/crates.io-index" dependencies = [ - "cc 1.0.31 (registry+https://github.com/rust-lang/crates.io-index)", + "cc 1.0.32 (registry+https://github.com/rust-lang/crates.io-index)", "libc 0.2.50 (registry+https://github.com/rust-lang/crates.io-index)", "libz-sys 1.0.25 (registry+https://github.com/rust-lang/crates.io-index)", - "openssl-sys 0.9.42 (registry+https://github.com/rust-lang/crates.io-index)", + "openssl-sys 0.9.43 (registry+https://github.com/rust-lang/crates.io-index)", "pkg-config 0.3.14 (registry+https://github.com/rust-lang/crates.io-index)", "vcpkg 0.2.6 (registry+https://github.com/rust-lang/crates.io-index)", ] @@ -491,7 +512,7 @@ name = "libz-sys" version = "1.0.25" source = "registry+https://github.com/rust-lang/crates.io-index" dependencies = [ - "cc 1.0.31 (registry+https://github.com/rust-lang/crates.io-index)", + "cc 1.0.32 (registry+https://github.com/rust-lang/crates.io-index)", "libc 0.2.50 (registry+https://github.com/rust-lang/crates.io-index)", "pkg-config 0.3.14 (registry+https://github.com/rust-lang/crates.io-index)", "vcpkg 0.2.6 (registry+https://github.com/rust-lang/crates.io-index)", @@ -607,10 +628,10 @@ source = "registry+https://github.com/rust-lang/crates.io-index" [[package]] name = "openssl-sys" -version = "0.9.42" +version = "0.9.43" source = "registry+https://github.com/rust-lang/crates.io-index" dependencies = [ - "cc 1.0.31 (registry+https://github.com/rust-lang/crates.io-index)", + "cc 1.0.32 (registry+https://github.com/rust-lang/crates.io-index)", "libc 0.2.50 (registry+https://github.com/rust-lang/crates.io-index)", "pkg-config 0.3.14 (registry+https://github.com/rust-lang/crates.io-index)", "rustc_version 0.2.3 (registry+https://github.com/rust-lang/crates.io-index)", @@ -895,6 +916,21 @@ dependencies = [ "winapi-util 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)", ] +[[package]] +name = "sapling-crypto" +version = "0.0.4" +source = "git+https://github.com/matterinc/sapling-crypto?tag=0.0.4#6ac48e2f920bd54358b7a4cca0a96f87753009e4" +dependencies = [ + "bellman 0.2.0 (git+https://github.com/matterinc/bellman?tag=0.2.0)", + "blake2-rfc 0.2.18 (git+https://github.com/gtank/blake2-rfc?rev=7a5b5fc99ae483a0043db7547fb79a6fa44b88a9)", + "byteorder 1.3.1 (registry+https://github.com/rust-lang/crates.io-index)", + "digest 0.7.6 (registry+https://github.com/rust-lang/crates.io-index)", + "rand 0.4.6 (registry+https://github.com/rust-lang/crates.io-index)", + "serde 1.0.89 (registry+https://github.com/rust-lang/crates.io-index)", + "serde_derive 1.0.89 (registry+https://github.com/rust-lang/crates.io-index)", + "tiny-keccak 1.4.2 (registry+https://github.com/rust-lang/crates.io-index)", +] + [[package]] name = "scopeguard" version = "0.3.3" @@ -1040,6 +1076,19 @@ dependencies = [ "lazy_static 1.3.0 (registry+https://github.com/rust-lang/crates.io-index)", ] +[[package]] +name = "tiny-keccak" +version = "1.4.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +dependencies = [ + "crunchy 0.1.6 (registry+https://github.com/rust-lang/crates.io-index)", +] + +[[package]] +name = "typenum" +version = "1.10.0" +source = "registry+https://github.com/rust-lang/crates.io-index" + [[package]] name = "ucd-util" version = "0.1.3" @@ -1167,8 +1216,8 @@ dependencies = [ "bellman 0.2.0 (git+https://github.com/matterinc/bellman?tag=0.2.0)", "bimap 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)", "bincode 0.8.0 (registry+https://github.com/rust-lang/crates.io-index)", - "cc 1.0.31 (registry+https://github.com/rust-lang/crates.io-index)", - "cmake 0.1.35 (registry+https://github.com/rust-lang/crates.io-index)", + "cc 1.0.32 (registry+https://github.com/rust-lang/crates.io-index)", + "cmake 0.1.37 (registry+https://github.com/rust-lang/crates.io-index)", "ff 0.5.0 (git+https://github.com/matterinc/ff?tag=0.5)", "git2 0.8.0 (registry+https://github.com/rust-lang/crates.io-index)", "glob 0.2.11 (registry+https://github.com/rust-lang/crates.io-index)", @@ -1187,6 +1236,16 @@ dependencies = [ "serde_derive 1.0.89 (registry+https://github.com/rust-lang/crates.io-index)", "serde_json 1.0.39 (registry+https://github.com/rust-lang/crates.io-index)", "wasmi 0.4.4 (registry+https://github.com/rust-lang/crates.io-index)", + "zokrates_embed 0.1.0", + "zokrates_field 0.3.2", +] + +[[package]] +name = "zokrates_embed" +version = "0.1.0" +dependencies = [ + "bellman 0.2.0 (git+https://github.com/matterinc/bellman?tag=0.2.0)", + "sapling-crypto 0.0.4 (git+https://github.com/matterinc/sapling-crypto?tag=0.0.4)", "zokrates_field 0.3.2", ] @@ -1245,11 +1304,11 @@ dependencies = [ "checksum bytecount 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)" = "b92204551573580e078dc80017f36a213eb77a0450e4ddd8cfa0f3f2d1f0178f" "checksum byteorder 1.3.1 (registry+https://github.com/rust-lang/crates.io-index)" = "a019b10a2a7cdeb292db131fc8113e57ea2a908f6e7894b0c3c671893b65dbeb" "checksum cargo_metadata 0.6.4 (registry+https://github.com/rust-lang/crates.io-index)" = "e5d1b4d380e1bab994591a24c2bdd1b054f64b60bef483a8c598c7c345bc3bbe" -"checksum cc 1.0.31 (registry+https://github.com/rust-lang/crates.io-index)" = "c9ce8bb087aacff865633f0bd5aeaed910fe2fe55b55f4739527f2e023a2e53d" +"checksum cc 1.0.32 (registry+https://github.com/rust-lang/crates.io-index)" = "ad0daef304fa0b4238f5f7ed7178774b43b06f6a9b6509f6642bef4ff1f7b9b2" "checksum cfg-if 0.1.7 (registry+https://github.com/rust-lang/crates.io-index)" = "11d43355396e872eefb45ce6342e4374ed7bc2b3a502d1b28e36d6e23c05d1f4" "checksum clap 2.32.0 (registry+https://github.com/rust-lang/crates.io-index)" = "b957d88f4b6a63b9d70d5f454ac8011819c6efa7727858f458ab71c756ce2d3e" "checksum cloudabi 0.0.3 (registry+https://github.com/rust-lang/crates.io-index)" = "ddfc5b9aa5d4507acaf872de71051dfd0e309860e88966e1051e462a077aac4f" -"checksum cmake 0.1.35 (registry+https://github.com/rust-lang/crates.io-index)" = "6ec65ee4f9c9d16f335091d23693457ed4928657ba4982289d7fafee03bc614a" +"checksum cmake 0.1.37 (registry+https://github.com/rust-lang/crates.io-index)" = "c11b79fbf026d6ec02704f7248c6da99be02068bf57f624bb08af72ad29f2c06" "checksum colored 1.7.0 (registry+https://github.com/rust-lang/crates.io-index)" = "6e9a455e156a4271e12fd0246238c380b1e223e3736663c7a18ed8b6362028a9" "checksum constant_time_eq 0.1.3 (registry+https://github.com/rust-lang/crates.io-index)" = "8ff012e225ce166d4422e0e78419d901719760f62ae2b7969ca6b564d1b54a9e" "checksum crossbeam 0.7.1 (registry+https://github.com/rust-lang/crates.io-index)" = "b14492071ca110999a20bf90e3833406d5d66bfd93b4e52ec9539025ff43fe0d" @@ -1261,10 +1320,12 @@ dependencies = [ "checksum crossbeam-queue 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)" = "7c979cd6cfe72335896575c6b5688da489e420d36a27a0b9eb0c73db574b4a4b" "checksum crossbeam-utils 0.2.2 (registry+https://github.com/rust-lang/crates.io-index)" = "2760899e32a1d58d5abb31129f8fae5de75220bc2176e77ff7c627ae45c918d9" "checksum crossbeam-utils 0.6.5 (registry+https://github.com/rust-lang/crates.io-index)" = "f8306fcef4a7b563b76b7dd949ca48f52bc1141aa067d2ea09565f3e2652aa5c" +"checksum crunchy 0.1.6 (registry+https://github.com/rust-lang/crates.io-index)" = "a2f4a431c5c9f662e1200b7c7f02c34e91361150e382089a8f2dec3ba680cbda" "checksum csv 1.0.5 (registry+https://github.com/rust-lang/crates.io-index)" = "9fd1c44c58078cfbeaf11fbb3eac9ae5534c23004ed770cc4bfb48e658ae4f04" "checksum csv-core 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)" = "fa5cdef62f37e6ffe7d1f07a381bc0db32b7a3ff1cac0de56cb0d81e71f53d65" "checksum curl-sys 0.4.17 (registry+https://github.com/rust-lang/crates.io-index)" = "7b8d8e51964f58c8053337fcef48e1c4608c7ee70c6f2e457674a97dda5a5828" "checksum difference 1.0.0 (registry+https://github.com/rust-lang/crates.io-index)" = "b3304d19798a8e067e48d8e69b2c37f0b5e9b4e462504ad9e27e9f3fce02bba8" +"checksum digest 0.7.6 (registry+https://github.com/rust-lang/crates.io-index)" = "03b072242a8cbaf9c145665af9d250c59af3b958f83ed6824e13533cf76d5b90" "checksum either 1.5.1 (registry+https://github.com/rust-lang/crates.io-index)" = "c67353c641dc847124ea1902d69bd753dee9bb3beff9aa3662ecf86c971d1fac" "checksum environment 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)" = "1f4b14e20978669064c33b4c1e0fb4083412e40fe56cbea2eae80fd7591503ee" "checksum error-chain 0.11.0 (registry+https://github.com/rust-lang/crates.io-index)" = "ff511d5dc435d703f4971bc399647c9bc38e20cb41452e3b9feb4765419ed3f3" @@ -1274,6 +1335,7 @@ dependencies = [ "checksum fuchsia-cprng 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)" = "a06f77d526c1a601b7c4cdd98f54b5eaabffc14d5f2f0296febdc7f357c6d3ba" "checksum futures 0.1.25 (registry+https://github.com/rust-lang/crates.io-index)" = "49e7653e374fe0d0c12de4250f0bdb60680b8c80eed558c5c7538eec9c89e21b" "checksum futures-cpupool 0.1.8 (registry+https://github.com/rust-lang/crates.io-index)" = "ab90cde24b3319636588d0c35fe03b1333857621051837ed769faefb4c2162e4" +"checksum generic-array 0.9.0 (registry+https://github.com/rust-lang/crates.io-index)" = "ef25c5683767570c2bbd7deba372926a55eaae9982d7726ee2a1050239d45b9d" "checksum git2 0.8.0 (registry+https://github.com/rust-lang/crates.io-index)" = "c7339329bfa14a00223244311560d11f8f489b453fb90092af97f267a6090ab0" "checksum glob 0.2.11 (registry+https://github.com/rust-lang/crates.io-index)" = "8be18de09a56b60ed0edf84bc9df007e30040691af7acd1c41874faac5895bfb" "checksum glob 0.3.0 (registry+https://github.com/rust-lang/crates.io-index)" = "9b919933a397b79c37e33b77bb2aa3dc8eb6e165ad809e58ff75bc7db2e34574" @@ -1301,7 +1363,7 @@ dependencies = [ "checksum num-traits 0.2.6 (registry+https://github.com/rust-lang/crates.io-index)" = "0b3a5d7cc97d6d30d8b9bc8fa19bf45349ffe46241e8816f50f62f6d6aaabee1" "checksum num_cpus 1.10.0 (registry+https://github.com/rust-lang/crates.io-index)" = "1a23f0ed30a54abaa0c7e83b1d2d87ada7c3c23078d1d87815af3e3b6385fbba" "checksum openssl-probe 0.1.2 (registry+https://github.com/rust-lang/crates.io-index)" = "77af24da69f9d9341038eba93a073b1fdaaa1b788221b00a69bce9e762cb32de" -"checksum openssl-sys 0.9.42 (registry+https://github.com/rust-lang/crates.io-index)" = "cb534d752bf98cf363b473950659ac2546517f9c6be9723771614ab3f03bbc9e" +"checksum openssl-sys 0.9.43 (registry+https://github.com/rust-lang/crates.io-index)" = "33c86834957dd5b915623e94f2f4ab2c70dd8f6b70679824155d5ae21dbd495d" "checksum pairing 0.16.2 (git+https://github.com/matterinc/pairing?tag=0.16.2)" = "" "checksum parity-wasm 0.31.3 (registry+https://github.com/rust-lang/crates.io-index)" = "511379a8194230c2395d2f5fa627a5a7e108a9f976656ce723ae68fca4097bfc" "checksum parity-wasm 0.35.7 (registry+https://github.com/rust-lang/crates.io-index)" = "3e1e076c4e01399b6cd0793a8df42f90bba3ae424671ef421d1608a943155d93" @@ -1335,6 +1397,7 @@ dependencies = [ "checksum rustc_version 0.2.3 (registry+https://github.com/rust-lang/crates.io-index)" = "138e3e0acb6c9fb258b19b67cb8abd63c00679d2851805ea151465464fe9030a" "checksum ryu 0.2.7 (registry+https://github.com/rust-lang/crates.io-index)" = "eb9e9b8cde282a9fe6a42dd4681319bfb63f121b8a8ee9439c6f4107e58a46f7" "checksum same-file 1.0.4 (registry+https://github.com/rust-lang/crates.io-index)" = "8f20c4be53a8a1ff4c1f1b2bd14570d2f634628709752f0702ecdd2b3f9a5267" +"checksum sapling-crypto 0.0.4 (git+https://github.com/matterinc/sapling-crypto?tag=0.0.4)" = "" "checksum scopeguard 0.3.3 (registry+https://github.com/rust-lang/crates.io-index)" = "94258f53601af11e6a49f722422f6e3425c52b06245a5cf9bc09908b174f5e27" "checksum semver 0.9.0 (registry+https://github.com/rust-lang/crates.io-index)" = "1d7eb9ef2c18661902cc47e535f9bc51b78acd254da71d375c2f6720d9a40403" "checksum semver-parser 0.7.0 (registry+https://github.com/rust-lang/crates.io-index)" = "388a1df253eca08550bef6c72392cfe7c30914bf41df5269b68cbd6ff8f570a3" @@ -1352,6 +1415,8 @@ dependencies = [ "checksum termion 1.5.1 (registry+https://github.com/rust-lang/crates.io-index)" = "689a3bdfaab439fd92bc87df5c4c78417d3cbe537487274e9b0b2dce76e92096" "checksum textwrap 0.10.0 (registry+https://github.com/rust-lang/crates.io-index)" = "307686869c93e71f94da64286f9a9524c0f308a9e1c87a583de8e9c9039ad3f6" "checksum thread_local 0.3.6 (registry+https://github.com/rust-lang/crates.io-index)" = "c6b53e329000edc2b34dbe8545fd20e55a333362d0a321909685a19bd28c3f1b" +"checksum tiny-keccak 1.4.2 (registry+https://github.com/rust-lang/crates.io-index)" = "e9175261fbdb60781fcd388a4d6cc7e14764a2b629a7ad94abb439aed223a44f" +"checksum typenum 1.10.0 (registry+https://github.com/rust-lang/crates.io-index)" = "612d636f949607bdf9b123b4a6f6d966dedf3ff669f7f045890d3a4a73948169" "checksum ucd-util 0.1.3 (registry+https://github.com/rust-lang/crates.io-index)" = "535c204ee4d8434478593480b8f86ab45ec9aae0e83c568ca81abf0fd0e88f86" "checksum unicode-bidi 0.3.4 (registry+https://github.com/rust-lang/crates.io-index)" = "49f2bd0c6468a8230e1db229cff8029217cf623c767ea5d60bfbd42729ea54d5" "checksum unicode-normalization 0.1.8 (registry+https://github.com/rust-lang/crates.io-index)" = "141339a08b982d942be2ca06ff8b076563cbe223d1befd5450716790d44e2426" diff --git a/Cargo.toml b/Cargo.toml index ba708ea5..0e12445e 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -5,4 +5,5 @@ members = [ "zokrates_cli", "zokrates_fs_resolver", "zokrates_stdlib", + "zokrates_embed", ] \ No newline at end of file diff --git a/zokrates_core/Cargo.toml b/zokrates_core/Cargo.toml index 10c03e3b..733fd0b3 100644 --- a/zokrates_core/Cargo.toml +++ b/zokrates_core/Cargo.toml @@ -29,6 +29,7 @@ bellman = { git = "https://github.com/matterinc/bellman", tag = "0.2.0" } pairing = { git = "https://github.com/matterinc/pairing", tag = "0.16.2" } ff = { git = 'https://github.com/matterinc/ff', features = ["derive"], tag = "0.5" } zokrates_field = { version = "0.3.0", path = "../zokrates_field" } +zokrates_embed = { path = "../zokrates_embed" } rand = "0.4" wasmi = "0.4.2" parity-wasm = "0.35.3" diff --git a/zokrates_core/build.rs b/zokrates_core/build.rs index 3cf7de02..b70deb5c 100644 --- a/zokrates_core/build.rs +++ b/zokrates_core/build.rs @@ -57,18 +57,6 @@ fn main() { .file("lib/pghr13.cpp") .compile("libwraplibsnark.a"); - // build gadgets - - cc::Build::new() - .cpp(true) - .flag("-std=c++11") - .include(libsnark_source_path) - .include(libsnark_source_path.join("depends/libff")) - .include(libsnark_source_path.join("depends/libfqfft")) - .define("CURVE_ALT_BN128", None) - .file("lib/wraplibsnarkgadgets.cpp") - .compile("libwraplibsnarkgadgets.a"); - println!( "cargo:rustc-link-search=native={}", libsnark.join("lib").display() diff --git a/zokrates_core/lib/wraplibsnarkgadgets.cpp b/zokrates_core/lib/wraplibsnarkgadgets.cpp deleted file mode 100644 index 954bd8e3..00000000 --- a/zokrates_core/lib/wraplibsnarkgadgets.cpp +++ /dev/null @@ -1,237 +0,0 @@ -//https://gist.github.com/kobigurk/24c25e68219df87c348f1a78db51bb52 -#include - -#include "wraplibsnarkgadgets.hpp" - -#include "libsnark/gadgetlib1/gadget.hpp" -#include "libsnark/gadgetlib1/protoboard.hpp" -#include "libff/common/default_types/ec_pp.hpp" -#include "libsnark/gadgetlib1/gadgets/hashes/sha256/sha256_components.hpp" -#include "libsnark/gadgetlib1/gadgets/hashes/sha256/sha256_gadget.hpp" - -using namespace libsnark; -using namespace libff; -using std::vector; - - -typedef libff::Fr FieldT; - -pb_variable_array from_bits(std::vector bits, pb_variable& ZERO) -{ - pb_variable_array acc; - - for (size_t i = 0; i < bits.size(); i++) { - bool bit = bits[i]; - acc.emplace_back(bit ? ONE : ZERO); - } - - return acc; -} - -vector bit_list_to_ints(vector bit_list, const size_t wordsize) -{ - vector res; - size_t iterations = bit_list.size()/wordsize+1; - for (size_t i = 0; i < iterations; ++i) { - unsigned long current = 0; - for (size_t j = 0; j < wordsize; ++j) { - if (bit_list.size() == (i*wordsize+j)) break; - current += (bit_list[i*wordsize+j] * (1ul<<(wordsize-1-j))); - } - res.push_back(current); - } - return res; -} -// conversion byte[32] <-> libsnark bigint. -libff::bigint libsnarkBigintFromBytesAux(const uint8_t* _x) -{ - libff::bigint x; - - for (unsigned i = 0; i < 4; i++) { - for (unsigned j = 0; j < 8; j++) { - x.data[3 - i] |= uint64_t(_x[i * 8 + j]) << (8 * (7-j)); - } - } - return x; -} - -void constraint_to_json(linear_combination constraints, std::stringstream &ss) -{ - ss << "{"; - uint count = 0; - for (const linear_term& lt : constraints.terms) - { - if (count != 0) { - ss << ","; - } - - ss << '"' << lt.index << '"' << ":" << '"' << lt.coeff << '"'; - count++; - } - ss << "}"; -} - - -std::string r1cs_to_json(protoboard pb) -{ - r1cs_constraint_system constraints = pb.get_constraint_system(); - std::stringstream ss; - - ss << "{\"variable_count\":"; - ss << pb.num_variables() + 1; // ~one is not counted in pb.num_variables() - ss << ",\"inputs\":[1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21,22,23,24,25,26,27,28,29,30,31,32,33,34,35,36,37,38,39,40,41,42,43,44,45,46,47,48,49,50,51,52,53,54,55,56,57,58,59,60,61,62,63,64,65,66,67,68,69,70,71,72,73,74,75,76,77,78,79,80,81,82,83,84,85,86,87,88,89,90,91,92,93,94,95,96,97,98,99,100,101,102,103,104,105,106,107,108,109,110,111,112,113,114,115,116,117,118,119,120,121,122,123,124,125,126,127,128,129,130,131,132,133,134,135,136,137,138,139,140,141,142,143,144,145,146,147,148,149,150,151,152,153,154,155,156,157,158,159,160,161,162,163,164,165,166,167,168,169,170,171,172,173,174,175,176,177,178,179,180,181,182,183,184,185,186,187,188,189,190,191,192,193,194,195,196,197,198,199,200,201,202,203,204,205,206,207,208,209,210,211,212,213,214,215,216,217,218,219,220,221,222,223,224,225,226,227,228,229,230,231,232,233,234,235,236,237,238,239,240,241,242,243,244,245,246,247,248,249,250,251,252,253,254,255,256,257,258,259,260,261,262,263,264,265,266,267,268,269,270,271,272,273,274,275,276,277,278,279,280,281,282,283,284,285,286,287,288,289,290,291,292,293,294,295,296,297,298,299,300,301,302,303,304,305,306,307,308,309,310,311,312,313,314,315,316,317,318,319,320,321,322,323,324,325,326,327,328,329,330,331,332,333,334,335,336,337,338,339,340,341,342,343,344,345,346,347,348,349,350,351,352,353,354,355,356,357,358,359,360,361,362,363,364,365,366,367,368,369,370,371,372,373,374,375,376,377,378,379,380,381,382,383,384,385,386,387,388,389,390,391,392,393,394,395,396,397,398,399,400,401,402,403,404,405,406,407,408,409,410,411,412,413,414,415,416,417,418,419,420,421,422,423,424,425,426,427,428,429,430,431,432,433,434,435,436,437,438,439,440,441,442,443,444,445,446,447,448,449,450,451,452,453,454,455,456,457,458,459,460,461,462,463,464,465,466,467,468,469,470,471,472,473,474,475,476,477,478,479,480,481,482,483,484,485,486,487,488,489,490,491,492,493,494,495,496,497,498,499,500,501,502,503,504,505,506,507,508,509,510,511,512,513,514,515,516,517,518,519,520,521,522,523,524,525,526,527,528,529,530,531,532,533,534,535,536,537,538,539,540,541,542,543,544,545,546,547,548,549,550,551,552,553,554,555,556,557,558,559,560,561,562,563,564,565,566,567,568,569,570,571,572,573,574,575,576,577,578,579,580,581,582,583,584,585,586,587,588,589,590,591,592,593,594,595,596,597,598,599,600,601,602,603,604,605,606,607,608,609,610,611,612,613,614,615,616,617,618,619,620,621,622,623,624,625,626,627,628,629,630,631,632,633,634,635,636,637,638,639,640,641,642,643,644,645,646,647,648,649,650,651,652,653,654,655,656,657,658,659,660,661,662,663,664,665,666,667,668,669,670,671,672,673,674,675,676,677,678,679,680,681,682,683,684,685,686,687,688,689,690,691,692,693,694,695,696,697,698,699,700,701,702,703,704,705,706,707,708,709,710,711,712,713,714,715,716,717,718,719,720,721,722,723,724,725,726,727,728,729,730,731,732,733,734,735,736,737,738,739,740,741,742,743,744,745,746,747,748,749,750,751,752,753,754,755,756,757,758,759,760,761,762,763,764,765,766,767,768], \"outputs\":[769,770,771,772,773,774,775,776,777,778,779,780,781,782,783,784,785,786,787,788,789,790,791,792,793,794,795,796,797,798,799,800,801,802,803,804,805,806,807,808,809,810,811,812,813,814,815,816,817,818,819,820,821,822,823,824,825,826,827,828,829,830,831,832,833,834,835,836,837,838,839,840,841,842,843,844,845,846,847,848,849,850,851,852,853,854,855,856,857,858,859,860,861,862,863,864,865,866,867,868,869,870,871,872,873,874,875,876,877,878,879,880,881,882,883,884,885,886,887,888,889,890,891,892,893,894,895,896,897,898,899,900,901,902,903,904,905,906,907,908,909,910,911,912,913,914,915,916,917,918,919,920,921,922,923,924,925,926,927,928,929,930,931,932,933,934,935,936,937,938,939,940,941,942,943,944,945,946,947,948,949,950,951,952,953,954,955,956,957,958,959,960,961,962,963,964,965,966,967,968,969,970,971,972,973,974,975,976,977,978,979,980,981,982,983,984,985,986,987,988,989,990,991,992,993,994,995,996,997,998,999,1000,1001,1002,1003,1004,1005,1006,1007,1008,1009,1010,1011,1012,1013,1014,1015,1016,1017,1018,1019,1020,1021,1022,1023,1024],\"constraints\":["; - - for (size_t c = 0; c < constraints.num_constraints(); ++c) - { - ss << "[";// << "\"A\"="; - constraint_to_json(constraints.constraints[c].a, ss); - ss << ",";// << "\"B\"="; - constraint_to_json(constraints.constraints[c].b, ss); - ss << ",";// << "\"C\"=";; - constraint_to_json(constraints.constraints[c].c, ss); - if (c == constraints.num_constraints()-1 ) { - ss << "]\n"; - } else { - ss << "],\n"; - } - } - ss << "]}"; - ss.rdbuf()->pubseekpos(0, std::ios_base::out); - return ss.str(); -} - -std::string array_to_json(protoboard pb) -{ - std::stringstream ss; - r1cs_variable_assignment values = pb.full_variable_assignment(); - ss << "{\"variables\":["; - - ss << 1 << ","; // the variable zero to the one constant - - for (size_t i = 0; i < values.size(); ++i) - { - ss << values[i].as_bigint(); - if (i < values.size() - 1) { ss << ",";} - } - - ss << "]}"; - - // std::cout << ss.rdbuf(); - - ss.rdbuf()->pubseekpos(0, std::ios_base::out); - - return(ss.str()); -} - -class sha256round: gadget -{ -private: - std::shared_ptr> block; - -public: - std::shared_ptr> hasher; - sha256round( - protoboard &pb, - pb_variable_array& myIV, - pb_variable_array& a, - pb_variable_array& b, - digest_variable &result - ) : gadget(pb, "sha256round") { - - block.reset(new block_variable(pb, { - a, - b - }, "block")); - - hasher.reset(new sha256_compression_function_gadget( - pb, - myIV, - block->bits, - result, - "hasher")); - } - - void generate_r1cs_constraints() { - hasher->generate_r1cs_constraints(); - } - - void generate_r1cs_witness() { - hasher->generate_r1cs_witness(); - } -}; - -char* _sha256RoundConstraints() -{ - libff::alt_bn128_pp::init_public_params(); - protoboard pb; - pb_variable_array left; - - left.allocate(pb, 256, "left"); - pb_variable_array right; - right.allocate(pb, 256, "right"); - - digest_variable IV(pb, 256, "IV"); - - digest_variable output(pb, 256, "output"); - - IV.generate_r1cs_constraints(); //binary check for IV vector - output.generate_r1cs_constraints(); //binary check for output vector - - sha256round g(pb, IV.bits, left, right, output); - g.generate_r1cs_constraints(); - - auto json = r1cs_to_json(pb); - - auto result = new char[json.size() + 1]; - memcpy(result, json.c_str(), json.size() + 1); - return result; -} - -char* _sha256RoundWitness(const uint8_t* inputs, int inputs_length) -{ - assert(inputs_length==768); - - libff::alt_bn128_pp::init_public_params(); - protoboard pb; - - pb_variable_array left; - left.allocate(pb, 256, "left"); - pb_variable_array right; - right.allocate(pb, 256, "right"); - - digest_variable IV(pb, 256, "IV"); - - digest_variable output(pb, 256, "output"); - - libff::bit_vector left_bv; - libff::bit_vector right_bv; - libff::bit_vector IV_bv; - - for (int i = 0; i < 256; i++) { - left_bv.push_back(libsnarkBigintFromBytesAux(inputs + i*32) == 1); - } - - for (int i = 256; i < 512; i++) { - right_bv.push_back(libsnarkBigintFromBytesAux(inputs + i*32) == 1); - } - - for (int i = 512; i < 768; i++) { - IV_bv.push_back(libsnarkBigintFromBytesAux(inputs + i*32) == 1); - } - - left.fill_with_bits(pb, left_bv); - right.fill_with_bits(pb, right_bv); - - IV.generate_r1cs_witness(IV_bv); - - sha256round g(pb, IV.bits, left, right, output); - g.generate_r1cs_witness(); - - assert(pb.is_satisfied()); - - auto json = array_to_json(pb); - - auto result = new char[json.size() + 1]; - memcpy(result, json.c_str(), json.size() + 1); - return result; -} diff --git a/zokrates_core/lib/wraplibsnarkgadgets.hpp b/zokrates_core/lib/wraplibsnarkgadgets.hpp deleted file mode 100644 index 1677e57e..00000000 --- a/zokrates_core/lib/wraplibsnarkgadgets.hpp +++ /dev/null @@ -1,25 +0,0 @@ -/** - * @file wraplibsnark.hpp - * @author Jacob Eberhardt - * @date 2017 - */ - -#ifdef __cplusplus -extern "C" { -#endif - -#include -#include - -char* _sha256RoundConstraints(); -char* _sha256RoundWitness(const uint8_t* input, int input_length); - -// External interface to free memory -void _free_string(char const *str) { - delete[] str; -} - -#ifdef __cplusplus -} // extern "C" -#endif diff --git a/zokrates_core/src/helpers/rust.rs b/zokrates_core/src/helpers/rust.rs index 5982030a..67f0ffe9 100644 --- a/zokrates_core/src/helpers/rust.rs +++ b/zokrates_core/src/helpers/rust.rs @@ -1,5 +1,6 @@ use helpers::{Executable, Signed}; use std::fmt; +use zokrates_embed::generate_sha256_round_witness; use zokrates_field::field::Field; #[derive(Clone, PartialEq, Debug, Serialize, Deserialize)] @@ -8,16 +9,12 @@ pub enum RustHelper { ConditionEq, Bits, Div, + Sha256Round, } impl fmt::Display for RustHelper { fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result { - match *self { - RustHelper::Identity => write!(f, "Identity"), - RustHelper::ConditionEq => write!(f, "ConditionEq"), - RustHelper::Bits => write!(f, "Bits"), - RustHelper::Div => write!(f, "Div"), - } + write!(f, "{:?}", self) } } @@ -28,6 +25,7 @@ impl Signed for RustHelper { RustHelper::ConditionEq => (1, 2), RustHelper::Bits => (1, 254), RustHelper::Div => (2, 1), + RustHelper::Sha256Round => (768, 26935), } } } @@ -56,6 +54,12 @@ impl Executable for RustHelper { Ok(res) } RustHelper::Div => Ok(vec![inputs[0].clone() / inputs[1].clone()]), + RustHelper::Sha256Round => { + let i = &inputs[0..512]; + let h = &inputs[512..]; + assert!(h.len() == 256); + Ok(generate_sha256_round_witness(i, h)) + } } } } diff --git a/zokrates_core/src/imports.rs b/zokrates_core/src/imports.rs index 2c439526..358c036e 100644 --- a/zokrates_core/src/imports.rs +++ b/zokrates_core/src/imports.rs @@ -139,40 +139,29 @@ impl Importer { let pos = import.pos(); let import = &import.value; // handle the case of special libsnark and packing imports - if import.source.starts_with("LIBSNARK") { - #[cfg(feature = "libsnark")] - { - use helpers::LibsnarkGadgetHelper; - use libsnark::get_sha256round_constraints; - use serde_json::from_str; - use standard::{DirectiveR1CS, R1CS}; + if import.source.starts_with("BELLMAN") { + match import.source.as_ref() { + "BELLMAN/sha256round" => { + use standard::sha_round; - match import.source.as_ref() { - "LIBSNARK/sha256round" => { - let r1cs: R1CS = from_str(&get_sha256round_constraints()).unwrap(); - let dr1cs: DirectiveR1CS = DirectiveR1CS { - r1cs, - directive: LibsnarkGadgetHelper::Sha256Round, - }; - let compiled = FlatProg::from(dr1cs); - let alias = match import.alias { - Some(ref alias) => alias.clone(), - None => String::from("sha256round"), - }; - origins.push(CompiledImport::new(compiled, alias)); - } - s => { - return Err(CompileErrorInner::ImportError( - Error::new(format!("Gadget {} not found", s)).with_pos(Some(pos)), - ) - .with_context(&location) - .into()); - } + let compiled = FlatProg { + functions: vec![sha_round()], + }; + + let alias = match import.alias { + Some(ref alias) => alias.clone(), + None => String::from("sha256round"), + }; + + origins.push(CompiledImport::new(compiled, alias)); + } + s => { + return Err(CompileErrorInner::ImportError( + Error::new(format!("Gadget {} not found", s)).with_pos(Some(pos)), + ) + .with_context(&location) + .into()); } - } - #[cfg(not(feature = "libsnark"))] - { - panic!("libsnark is not enabled, cannot access {}", import.source) } } else if import.source.starts_with("PACKING") { use types::conversions::split; diff --git a/zokrates_core/src/lib.rs b/zokrates_core/src/lib.rs index c43f2529..eb12410e 100644 --- a/zokrates_core/src/lib.rs +++ b/zokrates_core/src/lib.rs @@ -21,6 +21,7 @@ extern crate rustc_hex; extern crate serde_bytes; #[cfg(feature = "wasm")] extern crate wasmi; +extern crate zokrates_embed; extern crate zokrates_field; mod flatten; @@ -29,7 +30,6 @@ mod imports; mod optimizer; mod parser; mod semantics; -#[cfg(feature = "libsnark")] mod standard; mod static_analysis; mod typed_absy; @@ -39,7 +39,4 @@ pub mod absy; pub mod compile; pub mod flat_absy; pub mod ir; -#[cfg(feature = "libsnark")] -pub mod libsnark; -// #[cfg(feature = "libsnark")] pub mod proof_system; diff --git a/zokrates_core/src/libsnark.rs b/zokrates_core/src/libsnark.rs deleted file mode 100644 index 3cb0740f..00000000 --- a/zokrates_core/src/libsnark.rs +++ /dev/null @@ -1,132 +0,0 @@ -// -// @file libsnark.rs -// @author Jacob Eberhardt -// @date 2017 - -extern crate libc; - -use self::libc::{c_char, c_int, uint8_t}; -use std::ffi::CStr; -use std::string::String; - -use zokrates_field::field::Field; - -extern "C" { - fn _sha256RoundConstraints() -> *mut c_char; - fn _sha256RoundWitness(inputs: *const uint8_t, inputs_length: c_int) -> *mut c_char; - fn _free_string(str: *const c_char); -} - -pub fn get_sha256round_constraints() -> String { - let c_buf: *const c_char = unsafe { _sha256RoundConstraints() }; - let c_str: &CStr = unsafe { CStr::from_ptr(c_buf) }; - let str_slice: &str = c_str.to_str().unwrap(); - let str_buf: String = str_slice.to_owned(); //memory allocated in Rust - unsafe { _free_string(c_buf) }; //memory deallocated in Cpp - str_buf -} - -pub fn get_sha256round_witness(inputs: &Vec) -> String { - let mut inputs_arr: Vec<[u8; 32]> = vec![[0u8; 32]; inputs.len()]; - for (index, value) in inputs.into_iter().enumerate() { - inputs_arr[index] = vec_as_u8_32_array(&value.into_byte_vector()); - } - let c_buf: *const c_char = - unsafe { _sha256RoundWitness(inputs_arr[0].as_ptr(), inputs.len() as i32) }; - let c_str: &CStr = unsafe { CStr::from_ptr(c_buf) }; - let str_slice: &str = c_str.to_str().unwrap(); - let str_buf: String = str_slice.to_owned(); - unsafe { _free_string(c_buf) }; - str_buf -} - -// utility function. Converts a Fields vector-based byte representation to fixed size array. -fn vec_as_u8_32_array(vec: &Vec) -> [u8; 32] { - assert!(vec.len() <= 32); - let mut array = [0u8; 32]; - for (index, byte) in vec.iter().enumerate() { - array[31 - index] = *byte; - } - array -} - -#[cfg(test)] -mod tests { - use super::*; - use flat_absy::*; - use helpers; - use num_bigint::BigUint; - use serde_json; - use standard; - use zokrates_field::field::FieldPrime; - - #[cfg(test)] - mod sha256_gadget { - use super::*; - - #[test] - fn can_get_sha256_constraints() { - let _a = get_sha256round_constraints(); - } - - #[test] - fn can_generate_sha_256_witness_null() { - let inputs = vec![FieldPrime::from(0); 768]; - let _b = get_sha256round_witness(&inputs); - } - - #[test] - fn can_generate_flattened_code() { - let constraints = get_sha256round_constraints(); - let r1cs: standard::R1CS = serde_json::from_str(&constraints).unwrap(); - let _prog: FlatProg = FlatProg::from(standard::DirectiveR1CS { - r1cs, - directive: helpers::LibsnarkGadgetHelper::Sha256Round, - }); - } - } - - #[cfg(test)] - mod libsnark_integration { - use super::*; - - #[test] - fn serialization_dec() { - assert_eq!( - BigUint::parse_bytes( - b"5472060717959818805561601436314318772174077789324455915672259473661306552146", - 10 - ) - .unwrap() - .to_bytes_le(), - FieldPrime::try_from_str( - "5472060717959818805561601436314318772174077789324455915672259473661306552146" - ) - .unwrap() - .into_byte_vector() - ); - } - - #[test] - fn serialization_bin() { - assert_eq!( - BigUint::parse_bytes(b"110000011001000100111001110010111000010011000110100000001010011011100001010000010001011011011010000001100000010101100001011101100101111000000101101010100100010110100001110001110010101000110100111100001000001000110000010110110110000111110011111101010010",2).unwrap().to_bytes_le(), - FieldPrime::try_from_str("5472060717959818805561601436314318772174077789324455915672259473661306552146").unwrap().into_byte_vector() - ); - } - - #[test] - fn vec_to_array() { - let byte_vector: Vec = FieldPrime::try_from_str( - "5472060717959818805561601436314318772174077789324455915672259473661306552146", - ) - .unwrap() - .into_byte_vector(); - let array: [u8; 32] = vec_as_u8_32_array(&byte_vector); - for (index, value) in byte_vector.iter().enumerate() { - assert_eq!(*value, array[31 - index]); - } - } - } -} diff --git a/zokrates_core/src/proof_system/bn128/utils/bellman.rs b/zokrates_core/src/proof_system/bn128/utils/bellman.rs index 5d09a566..355b9c50 100644 --- a/zokrates_core/src/proof_system/bn128/utils/bellman.rs +++ b/zokrates_core/src/proof_system/bn128/utils/bellman.rs @@ -45,7 +45,7 @@ fn bellman_combination>( l.0.into_iter() .map(|(k, v)| { ( - Fr::from(v), + v.into_bellman(), symbols .entry(k) .or_insert_with(|| { @@ -57,7 +57,7 @@ fn bellman_combination>( .0 .remove(&k) .ok_or(SynthesisError::AssignmentMissing)? - .into()) + .into_bellman()) }, ), false => cs.alloc( @@ -67,7 +67,7 @@ fn bellman_combination>( .0 .remove(&k) .ok_or(SynthesisError::AssignmentMissing)? - .into()) + .into_bellman()) }, ), } @@ -107,7 +107,7 @@ impl Prog { .0 .remove(&var) .ok_or(SynthesisError::AssignmentMissing)? - .into()) + .into_bellman()) }, ), false => cs.alloc_input( @@ -117,7 +117,7 @@ impl Prog { .0 .remove(&var) .ok_or(SynthesisError::AssignmentMissing)? - .into()) + .into_bellman()) }, ), } @@ -172,7 +172,7 @@ impl Computation { .map(|(a, _)| a) .map(|v| self.witness.clone().unwrap().0.get(v).unwrap().clone()) .chain(self.witness.clone().unwrap().return_values()) - .map(|v| Fr::from(v.clone())) + .map(|v| v.clone().into_bellman()) .collect() } diff --git a/zokrates_core/src/standard.rs b/zokrates_core/src/standard.rs index b836911c..fb84706a 100644 --- a/zokrates_core/src/standard.rs +++ b/zokrates_core/src/standard.rs @@ -1,57 +1,18 @@ use flat_absy::{FlatExpression, FlatExpressionList, FlatFunction, FlatStatement}; use flat_absy::{FlatParameter, FlatVariable}; -use helpers::{DirectiveStatement, Helper, LibsnarkGadgetHelper}; +use helpers::{DirectiveStatement, Helper, RustHelper}; use reduce::Reduce; -use std::collections::BTreeMap; use types::{Signature, Type}; use zokrates_field::field::Field; -// for r1cs import, can be moved. -// r1cs data structure reflecting JSON standard format: -// { -// variable_count: 435, -// inputs: [offset_1, offset_33], // # of inputs to pass -// outputs: [offset_42, offset_63, offset_55], // indices of the outputs in the witness -// constraints: [ // constraints verified by the witness -// [ -// {offset_1: value_a1, offset_2: value_a2, ...}, -// {offset_1: value_b1, offset_2: value_b2, ...}, -// {offset_1: value_c1, offset_2: value_c2, ...} -// ] -// } -#[derive(Serialize, Deserialize, Debug)] -pub struct R1CS { - pub inputs: Vec, - pub outputs: Vec, - pub variable_count: usize, - pub constraints: Vec, -} - -#[derive(Serialize, Deserialize, Debug)] -pub struct Witness { - pub variables: Vec, -} - -#[derive(Serialize, Deserialize, Debug, PartialEq)] -pub struct Constraint { - a: BTreeMap, - b: BTreeMap, - c: BTreeMap, -} - -pub struct DirectiveR1CS { - pub r1cs: R1CS, - pub directive: LibsnarkGadgetHelper, -} - -impl Into> for Constraint { - fn into(self: Constraint) -> FlatStatement { - let rhs_a = match self +impl From> for FlatStatement { + fn from(c: zokrates_embed::Constraint) -> FlatStatement { + let rhs_a = match c .a .into_iter() .map(|(key, val)| { FlatExpression::Mult( - box FlatExpression::Number(T::from_dec_string(val.to_string())), + box FlatExpression::Number(val), box FlatExpression::Identifier(FlatVariable::new(key)), ) }) @@ -64,12 +25,12 @@ impl Into> for Constraint { None => FlatExpression::Number(T::zero()), }; - let rhs_b = match self + let rhs_b = match c .b .into_iter() .map(|(key, val)| { FlatExpression::Mult( - box FlatExpression::Number(T::from_dec_string(val.to_string())), + box FlatExpression::Number(val), box FlatExpression::Identifier(FlatVariable::new(key)), ) }) @@ -82,12 +43,12 @@ impl Into> for Constraint { None => FlatExpression::Number(T::zero()), }; - let lhs = match self + let lhs = match c .c .into_iter() .map(|(key, val)| { FlatExpression::Mult( - box FlatExpression::Number(T::from_dec_string(val.to_string())), + box FlatExpression::Number(val), box FlatExpression::Identifier(FlatVariable::new(key)), ) }) @@ -104,125 +65,142 @@ impl Into> for Constraint { } } -impl Into> for DirectiveR1CS { - fn into(self: DirectiveR1CS) -> FlatFunction { - let r1cs = self.r1cs; +pub fn sha_round() -> FlatFunction { + let (r1cs, input, current_hash, output) = zokrates_embed::generate_sha256_round_constraints(); - let variable_count = r1cs.variable_count; + let variable_count = r1cs.aux_count + 1; // auxiliary and ONE - let input_binding_statements = std::iter::once(FlatStatement::Condition( - FlatVariable::new(0).into(), - FlatExpression::Number(T::from(1)), - )) - .chain(r1cs.inputs.iter().enumerate().map(|(index, i)| { - FlatStatement::Condition( - FlatVariable::new(*i).into(), - FlatVariable::new(index + variable_count).into(), - ) - })); + // define the inputs with dummy variables: arguments to the function and to the directive + let input_variables: Vec = input + .iter() + .chain(current_hash.iter()) + .map(|i| FlatVariable::new(i + variable_count)) + .collect(); + let arguments = input_variables + .iter() + .map(|i| FlatParameter { + id: i.clone(), + private: true, + }) + .collect(); + let inputs: Vec> = input_variables + .into_iter() + .map(|i| FlatExpression::Identifier(i)) + .collect(); - // insert flattened statements to represent constraints - let constraint_statements = r1cs.constraints.into_iter().map(|c| c.into()); + let input_binding_statements = // bind first variable to ~one + std::iter::once(FlatStatement::Condition( + FlatVariable::new(0).into(), + FlatExpression::Number(T::from(1)), + )) + // bind input and current_hash to inputs + .chain(input.iter().chain(current_hash.iter()).map(|i| { + FlatStatement::Condition( + FlatVariable::new(*i).into(), + FlatVariable::new(i + variable_count).into(), + ) + })); - // define the entire witness - let variables = vec![0; variable_count] - .iter() - .enumerate() - .map(|(i, _)| FlatVariable::new(i)) - .collect(); + // insert flattened statements to represent constraints + let constraint_statements = r1cs.constraints.into_iter().map(|c| c.into()); - // define the inputs with dummy variables: arguments to the function and to the directive - let input_variables: Vec = (0..r1cs.inputs.len()) - .map(|i| FlatVariable::new(i + variable_count)) - .collect(); - let arguments = input_variables - .iter() - .map(|i| FlatParameter { - id: i.clone(), - private: true, - }) - .collect(); - let inputs: Vec> = input_variables - .into_iter() - .map(|i| FlatExpression::Identifier(i)) - .collect(); + // define the entire witness + let variables = (0..variable_count).map(|i| FlatVariable::new(i)).collect(); - // define which subset of the witness is returned - let outputs: Vec> = r1cs - .outputs - .into_iter() - .map(|o| FlatExpression::Identifier(FlatVariable::new(o))) - .collect(); + // define which subset of the witness is returned + let outputs: Vec> = output + .into_iter() + .map(|o| FlatExpression::Identifier(FlatVariable::new(o))) + .collect(); - let signature = Signature { - inputs: vec![Type::FieldElement; inputs.len()], - outputs: vec![Type::FieldElement; outputs.len()], - }; + let signature = Signature { + inputs: vec![Type::FieldElement; inputs.len()], + outputs: vec![Type::FieldElement; outputs.len()], + }; - // insert a directive to set the witness based on the libsnark gadget and inputs - let directive_statement = match self.directive { - LibsnarkGadgetHelper::Sha256Round => FlatStatement::Directive(DirectiveStatement { - outputs: variables, - inputs: inputs, - helper: Helper::LibsnarkGadget(LibsnarkGadgetHelper::Sha256Round), - }), - }; + // insert a directive to set the witness based on the libsnark gadget and inputs + let directive_statement = FlatStatement::Directive(DirectiveStatement { + outputs: variables, + inputs: inputs, + helper: Helper::Rust(RustHelper::Sha256Round), + }); - // insert a statement to return the subset of the witness - let return_statement = FlatStatement::Return(FlatExpressionList { - expressions: outputs, - }); + // insert a statement to return the subset of the witness + let return_statement = FlatStatement::Return(FlatExpressionList { + expressions: outputs, + }); - let statements = std::iter::once(directive_statement) - .chain(input_binding_statements) - .chain(constraint_statements) - .chain(std::iter::once(return_statement)) - .collect(); + let statements = std::iter::once(directive_statement) + .chain(input_binding_statements) + .chain(constraint_statements) + .chain(std::iter::once(return_statement)) + .collect(); - FlatFunction { - id: "main".to_owned(), - arguments, - statements, - signature, - } + FlatFunction { + id: "main".to_owned(), + arguments, + statements, + signature, } } #[cfg(test)] mod tests { use super::*; - use serde_json; use zokrates_field::field::FieldPrime; - #[test] - fn deserialize_constraint() { - let constraint = r#"[{"2026": "1"}, {"0": "1", "2026": "1751751751751751751751751751751751751751751"}, {"0": "0"}]"#; - let _c: Constraint = serde_json::from_str(constraint).unwrap(); - } - - #[test] - fn constraint_into_flat_statement() { - let constraint = r#"[{"2026": "1"}, {"0": "1", "2026": "1751751751751751751751751751751751751751751"}, {"0": "0"}]"#; - let c: Constraint = serde_json::from_str(constraint).unwrap(); - let _statement: FlatStatement = c.into(); - } - #[test] fn generate_sha256_constraints() { - use flat_absy::FlatProg; - use libsnark::get_sha256round_constraints; - let r1cs: R1CS = serde_json::from_str(&get_sha256round_constraints()).unwrap(); - let v_count = r1cs.variable_count; + let compiled = sha_round(); - let dr1cs: DirectiveR1CS = DirectiveR1CS { - r1cs, - directive: LibsnarkGadgetHelper::Sha256Round, - }; - let compiled: FlatProg = FlatProg::from(dr1cs); + // function should have a signature of 768 inputs and 256 outputs + assert_eq!( + compiled.signature, + Signature::new() + .inputs(vec![Type::FieldElement; 768]) + .outputs(vec![Type::FieldElement; 256]) + ); + + // function should have 768 inputs + assert_eq!(compiled.arguments.len(), 768,); + + // function should return 256 values + assert_eq!( + compiled + .statements + .iter() + .filter_map(|s| match s { + FlatStatement::Return(v) => Some(v), + _ => None, + }) + .next() + .unwrap() + .expressions + .len(), + 256, + ); + + // directive should take 768 inputs and return n_var outputs + let directive = compiled + .statements + .iter() + .filter_map(|s| match s { + FlatStatement::Directive(d) => Some(d.clone()), + _ => None, + }) + .next() + .unwrap(); + assert_eq!(directive.inputs.len(), 768); + assert_eq!(directive.outputs.len(), 26935); + // function input should be offset by variable_count + assert_eq!( + compiled.arguments[0].id, + FlatVariable::new(directive.outputs.len() + 1) + ); // libsnark variable #0: index 0 should equal 1 assert_eq!( - compiled.functions[0].statements[1], + compiled.statements[1], FlatStatement::Condition( FlatVariable::new(0).into(), FlatExpression::Number(FieldPrime::from(1)) @@ -231,11 +209,25 @@ mod tests { // libsnark input #0: index 1 should equal zokrates input #0: index v_count assert_eq!( - compiled.functions[0].statements[2], - FlatStatement::Condition( - FlatVariable::new(1).into(), - FlatVariable::new(v_count).into() - ) + compiled.statements[2], + FlatStatement::Condition(FlatVariable::new(1).into(), FlatVariable::new(26936).into()) ); + + let f = ::ir::Function::from(compiled); + let prog = ::ir::Prog { + main: f, + private: vec![true; 768], + }; + + //use rand::Rng; + + // let mut rng = rand::thread_rng(); + // let input: Vec<_> = (0..768).map(|_| { + // rng.gen_range(0, 2) + // }).collect(); + + let input = (0..512).map(|_| 0).chain((0..256).map(|_| 1)).collect(); + + prog.execute(&input).unwrap(); } } diff --git a/zokrates_embed/Cargo.toml b/zokrates_embed/Cargo.toml new file mode 100644 index 00000000..4d92695b --- /dev/null +++ b/zokrates_embed/Cargo.toml @@ -0,0 +1,10 @@ +[package] +name = "zokrates_embed" +version = "0.1.0" +authors = ["schaeff "] +edition = "2018" + +[dependencies] +sapling-crypto = { git = 'https://github.com/matterinc/sapling-crypto', tag = "0.0.4" } +bellman = { git = 'https://github.com/matterinc/bellman', tag = "0.2.0" } +zokrates_field = { path = "../zokrates_field" } \ No newline at end of file diff --git a/zokrates_embed/src/lib.rs b/zokrates_embed/src/lib.rs new file mode 100644 index 00000000..98dea5fb --- /dev/null +++ b/zokrates_embed/src/lib.rs @@ -0,0 +1,412 @@ +use bellman::pairing::Engine; +use bellman::ConstraintSystem; +use bellman::{Index, LinearCombination, SynthesisError, Variable}; +use sapling_crypto::circuit::boolean::{AllocatedBit, Boolean}; +use sapling_crypto::circuit::sha256::sha256_compression_function; +use sapling_crypto::circuit::uint32::UInt32; +use zokrates_field::field::Field; + +#[derive(Debug)] +struct BellmanR1CS { + aux_count: usize, + constraints: Vec>, +} + +impl BellmanR1CS { + pub fn new() -> Self { + BellmanR1CS { + aux_count: 0, + constraints: vec![], + } + } +} + +#[derive(Debug)] +struct BellmanWitness { + pub values: Vec, +} + +#[derive(Debug, PartialEq)] +struct BellmanConstraint { + pub a: Vec<(usize, E::Fr)>, + pub b: Vec<(usize, E::Fr)>, + pub c: Vec<(usize, E::Fr)>, +} + +#[derive(Debug, PartialEq)] +pub struct Constraint { + pub a: Vec<(usize, T)>, + pub b: Vec<(usize, T)>, + pub c: Vec<(usize, T)>, +} + +#[derive(Debug)] +pub struct R1CS { + pub aux_count: usize, + pub constraints: Vec>, +} + +fn sha256_round>( + mut cs: CS, + input: Option<&Vec>, + current_hash: Option<&Vec>, +) -> Result<(Vec, Vec, Vec), SynthesisError> { + let input_bits = (0..512) + .map(|i| { + AllocatedBit::alloc::( + &mut cs.namespace(|| format!("input_{}", i)), + Some(input.as_ref().unwrap()[i] == T::from(1)), + ) + .unwrap() + }) + .collect::>(); + + let input = input_bits + .iter() + .map(|i| Boolean::Is(i.clone())) + .collect::>(); + + let current_hash_bits = (0..256) + .map(|i| { + AllocatedBit::alloc::( + &mut cs.namespace(|| format!("current_hash_{}", i)), + Some(current_hash.as_ref().unwrap()[i] == T::from(1)), + ) + .unwrap() + }) + .collect::>(); + + let current_hash = current_hash_bits + .chunks(32) + .map(|chunk| { + UInt32::from_bits_be( + &chunk + .into_iter() + .map(|i| Boolean::Is(i.clone())) + .collect::>(), + ) + }) + .collect::>(); + + let res = + sha256_compression_function::(&mut cs, &input, ¤t_hash).unwrap(); + + let output_bits = res + .into_iter() + .flat_map(|u| u.into_bits_be()) + .map(|b| b.get_variable().unwrap().clone()) + .collect::>(); + + Ok(( + input_bits + .into_iter() + .map(|b| BellmanR1CS::::var_to_index(b.get_variable())) + .collect(), + current_hash_bits + .into_iter() + .map(|b| BellmanR1CS::::var_to_index(b.get_variable())) + .collect(), + output_bits + .into_iter() + .map(|b| BellmanR1CS::::var_to_index(b.get_variable())) + .collect(), + )) +} + +impl R1CS { + fn from_bellman(cs: BellmanR1CS) -> Self { + R1CS { + aux_count: cs.aux_count, + constraints: cs + .constraints + .into_iter() + .map(|c| Constraint::from_bellman(c)) + .collect(), + } + } +} + +impl Constraint { + fn from_bellman(cs: BellmanConstraint) -> Self { + let res = Constraint { + a: cs + .a + .into_iter() + .map(|(variable, coefficient)| (variable, T::from_bellman(coefficient))) + .collect(), + b: cs + .b + .into_iter() + .map(|(variable, coefficient)| (variable, T::from_bellman(coefficient))) + .collect(), + c: cs + .c + .into_iter() + .map(|(variable, coefficient)| (variable, T::from_bellman(coefficient))) + .collect(), + }; + res + } +} + +impl ConstraintSystem for BellmanWitness { + type Root = Self; + + fn alloc(&mut self, _annotation: A, f: F) -> Result + where + F: FnOnce() -> Result, + A: FnOnce() -> AR, + AR: Into, + { + // we only care about the value + let index = self.values.len(); + let var = Variable::new_unchecked(Index::Aux(index)); + self.values.push(f().unwrap()); + Ok(var) + } + + fn alloc_input(&mut self, _annotation: A, _f: F) -> Result + where + F: FnOnce() -> Result, + A: FnOnce() -> AR, + AR: Into, + { + unreachable!("Bellman helpers are not allowed to allocate public variables") + } + + fn enforce(&mut self, _annotation: A, _a: LA, _b: LB, _c: LC) + where + A: FnOnce() -> AR, + AR: Into, + LA: FnOnce(LinearCombination) -> LinearCombination, + LB: FnOnce(LinearCombination) -> LinearCombination, + LC: FnOnce(LinearCombination) -> LinearCombination, + { + // do nothing + } + + fn push_namespace(&mut self, _name_fn: N) + where + NR: Into, + N: FnOnce() -> NR, + { + // do nothing + } + + fn pop_namespace(&mut self) { + // do nothing + } + + fn get_root(&mut self) -> &mut Self::Root { + self + } +} + +impl ConstraintSystem for BellmanR1CS { + type Root = Self; + + fn alloc(&mut self, _annotation: A, _f: F) -> Result + where + F: FnOnce() -> Result, + A: FnOnce() -> AR, + AR: Into, + { + // we don't care about the value as we're only getting the CS + let index = self.aux_count; + let var = Variable::new_unchecked(Index::Aux(index)); + self.aux_count += 1; + Ok(var) + } + + fn alloc_input(&mut self, _annotation: A, _f: F) -> Result + where + F: FnOnce() -> Result, + A: FnOnce() -> AR, + AR: Into, + { + unreachable!("Bellman helpers are not allowed to allocate public variables") + } + + fn enforce(&mut self, _annotation: A, a: LA, b: LB, c: LC) + where + A: FnOnce() -> AR, + AR: Into, + LA: FnOnce(LinearCombination) -> LinearCombination, + LB: FnOnce(LinearCombination) -> LinearCombination, + LC: FnOnce(LinearCombination) -> LinearCombination, + { + let a = a(LinearCombination::zero()); + let b = b(LinearCombination::zero()); + let c = c(LinearCombination::zero()); + + let a = a + .as_ref() + .into_iter() + .map(|(variable, coefficient)| { + (BellmanR1CS::::var_to_index(*variable), *coefficient) + }) + .collect(); + let b = b + .as_ref() + .into_iter() + .map(|(variable, coefficient)| { + (BellmanR1CS::::var_to_index(*variable), *coefficient) + }) + .collect(); + let c = c + .as_ref() + .into_iter() + .map(|(variable, coefficient)| { + (BellmanR1CS::::var_to_index(*variable), *coefficient) + }) + .collect(); + + self.constraints.push(BellmanConstraint { a, b, c }); + } + + fn push_namespace(&mut self, _name_fn: N) + where + NR: Into, + N: FnOnce() -> NR, + { + // do nothing + } + + fn pop_namespace(&mut self) { + // do nothing + } + + fn get_root(&mut self) -> &mut Self::Root { + self + } +} + +pub fn generate_xor_constraints() -> (R1CS, usize) { + let mut cs = BellmanR1CS::new(); + + let i0 = Boolean::Is(AllocatedBit::alloc::(&mut cs, None).unwrap()); + let i1 = Boolean::Is(AllocatedBit::alloc::(&mut cs, None).unwrap()); + + let res = Boolean::xor(&mut cs, &i0, &i1).unwrap(); + let res = + BellmanR1CS::::var_to_index(res.get_variable().unwrap().get_variable()); + + let cs = R1CS::from_bellman(cs); + + (cs, res) +} + +pub fn generate_xor_witness(i1: bool, i2: bool) -> Vec { + let mut cs = BellmanWitness { + values: vec![T::from(1).into_bellman()], + }; + + let i0 = Boolean::Is(AllocatedBit::alloc::(&mut cs, Some(i1)).unwrap()); + let i1 = Boolean::Is(AllocatedBit::alloc::(&mut cs, Some(i2)).unwrap()); + + Boolean::xor(&mut cs, &i0, &i1).unwrap(); + + cs.values.into_iter().map(|v| T::from_bellman(v)).collect() +} + +pub fn generate_sha256_round_constraints() -> (R1CS, Vec, Vec, Vec) +{ + let mut cs = BellmanR1CS::new(); + + let (input_bits, current_hash_bits, output_bits) = sha256_round::( + &mut cs, + Some(&vec![T::from(0); 512]), + Some(&vec![T::from(0); 256]), + ) + .unwrap(); + + // res is now the allocated bits for input, current_hash and sha256_output + + let cs = R1CS::::from_bellman(cs); + + (cs, input_bits, current_hash_bits, output_bits) +} + +pub fn generate_sha256_round_witness(input: &[T], current_hash: &[T]) -> Vec { + assert_eq!(input.len(), 512); + assert_eq!(current_hash.len(), 256); + + let mut cs = BellmanWitness { + values: vec![T::from(1).into_bellman()], + }; + + sha256_round(&mut cs, Some(&input.to_vec()), Some(¤t_hash.to_vec())).unwrap(); + + cs.values.into_iter().map(|v| T::from_bellman(v)).collect() +} + +impl BellmanR1CS { + fn var_to_index(v: Variable) -> usize { + match v.get_unchecked() { + Index::Aux(i) => i + 1, + Index::Input(0) => 0, + _ => unreachable!(), + } + } +} + +#[cfg(test)] +mod tests { + use super::*; + use zokrates_field::field::FieldPrime; + + #[test] + fn generate_constraints() { + let (_c, input, current_hash, output) = generate_sha256_round_constraints::(); + assert_eq!(input.len(), 512); + assert_eq!(current_hash.len(), 256); + assert_eq!(output.len(), 256); + } + + #[test] + fn generate_witness() { + let witness = generate_sha256_round_witness( + &vec![FieldPrime::from(0); 512], + &vec![FieldPrime::from(0); 256], + ); + assert_eq!(witness.len(), 26935); + } + + #[test] + fn xor() { + let (_, indice) = generate_xor_constraints::(); + + assert_eq!( + FieldPrime::from(0), + generate_xor_witness::(true, true)[indice] + ); + assert_eq!( + FieldPrime::from(1), + generate_xor_witness::(true, false)[indice] + ); + assert_eq!( + FieldPrime::from(1), + generate_xor_witness::(false, true)[indice] + ); + assert_eq!( + FieldPrime::from(0), + generate_xor_witness::(false, false)[indice] + ); + } + + #[test] + fn test_cs() { + use sapling_crypto::circuit::test::TestConstraintSystem; + + let mut cs = TestConstraintSystem::new(); + + let _ = sha256_round::( + &mut cs, + Some(&vec![FieldPrime::from(0); 512]), + Some(&vec![FieldPrime::from(1); 256]), + ) + .unwrap(); + + assert!(cs.is_satisfied()); + } +} diff --git a/zokrates_field/src/conversion.rs b/zokrates_field/src/conversion.rs deleted file mode 100644 index aeac2714..00000000 --- a/zokrates_field/src/conversion.rs +++ /dev/null @@ -1,84 +0,0 @@ -use crate::field::{Field, FieldPrime}; -use ff::{PrimeField, PrimeFieldRepr}; -use pairing::bn256::Fr; - -impl From for Fr { - fn from(e: FieldPrime) -> Fr { - let s = e.to_dec_string(); - Fr::from_str(&s).unwrap() - } -} - -impl From for FieldPrime { - fn from(e: Fr) -> FieldPrime { - let mut res: Vec = vec![]; - e.into_repr().write_le(&mut res).unwrap(); - FieldPrime::from_byte_vector(res) - } -} - -#[cfg(test)] -mod tests { - use super::*; - use ff::Field; - - extern crate rand; - use rand::{thread_rng, Rng}; - - #[test] - fn fr_to_field_to_fr() { - let rng = &mut thread_rng(); - let a: Fr = rng.gen(); - - assert_eq!(Fr::from(FieldPrime::from(a)), a); - } - - #[test] - fn field_to_fr_to_field() { - // use Fr to get a random element - let rng = &mut thread_rng(); - let a: Fr = rng.gen(); - - // now test idempotence - let a = FieldPrime::from(a); - - assert_eq!(FieldPrime::from(Fr::from(a.clone())), a); - } - - #[test] - fn one() { - let a = FieldPrime::from(1); - - assert_eq!(Fr::from(a), Fr::one()); - } - - #[test] - fn zero() { - let a = FieldPrime::from(0); - - assert_eq!(Fr::from(a), Fr::zero()); - } - - #[test] - fn minus_one() { - let mut a: Fr = Fr::one(); - a.negate(); - assert_eq!(FieldPrime::from(a), FieldPrime::from(-1)); - } - - #[test] - fn add() { - let rng = &mut thread_rng(); - - let mut a: Fr = rng.gen(); - let b: Fr = rng.gen(); - - let aa = FieldPrime::from(a); - let bb = FieldPrime::from(b); - let cc = aa + bb; - - a.add_assign(&b); - - assert_eq!(FieldPrime::from(a), cc); - } -} diff --git a/zokrates_field/src/field.rs b/zokrates_field/src/field.rs index 92e3abda..d5e0f6dc 100644 --- a/zokrates_field/src/field.rs +++ b/zokrates_field/src/field.rs @@ -8,6 +8,9 @@ use lazy_static::lazy_static; use num_bigint::{BigInt, BigUint, Sign, ToBigInt}; use num_integer::Integer; use num_traits::{Num, One, Zero}; +use pairing::bn256::Bn256; +use pairing::ff::ScalarEngine; +use pairing::Engine; use serde_derive::{Deserialize, Serialize}; use std::convert::From; use std::fmt; @@ -53,6 +56,22 @@ pub trait Field: + Pow + for<'a> Pow<&'a Self, Output = Self> { + /// An associated type to be able to operate with Bellman ff traits + type BellmanEngine: Engine; + + fn from_bellman(e: ::Fr) -> Self { + use ff::{PrimeField, PrimeFieldRepr}; + let mut res: Vec = vec![]; + e.into_repr().write_le(&mut res).unwrap(); + Self::from_byte_vector(res) + } + + fn into_bellman(self) -> ::Fr { + use ff::PrimeField; + let s = self.to_dec_string(); + ::Fr::from_str(&s).unwrap() + } + /// Returns this `Field`'s contents as little-endian byte vector fn into_byte_vector(&self) -> Vec; /// Returns an element of this `Field` from a little-endian byte vector @@ -82,6 +101,8 @@ pub struct FieldPrime { } impl Field for FieldPrime { + type BellmanEngine = Bn256; + fn into_byte_vector(&self) -> Vec { match self.value.to_biguint() { Option::Some(val) => val.to_bytes_le(), @@ -716,4 +737,74 @@ mod tests { s_field ); } + + mod bellman { + use super::*; + + use ff::Field as FField; + + extern crate rand; + use pairing::bn256::Fr; + use rand::{thread_rng, Rng}; + use Field; + + #[test] + fn fr_to_field_to_fr() { + let rng = &mut thread_rng(); + for _ in 0..1000 { + let a: Fr = rng.gen(); + assert_eq!(FieldPrime::from_bellman(a).into_bellman(), a); + } + } + + #[test] + fn field_to_fr_to_field() { + // use Fr to get a random element + let rng = &mut thread_rng(); + for _ in 0..1000 { + let a: Fr = rng.gen(); + // now test idempotence + let a = FieldPrime::from_bellman(a); + assert_eq!(FieldPrime::from_bellman(a.clone().into_bellman()), a); + } + } + + #[test] + fn one() { + let a = FieldPrime::from(1); + + assert_eq!(a.into_bellman(), Fr::one()); + } + + #[test] + fn zero() { + let a = FieldPrime::from(0); + + assert_eq!(a.into_bellman(), Fr::zero()); + } + + #[test] + fn minus_one() { + let mut a: Fr = Fr::one(); + a.negate(); + assert_eq!(FieldPrime::from_bellman(a), FieldPrime::from(-1)); + } + + #[test] + fn add() { + let rng = &mut thread_rng(); + + let mut a: Fr = rng.gen(); + let b: Fr = rng.gen(); + + let aa = FieldPrime::from_bellman(a); + let bb = FieldPrime::from_bellman(b); + let cc = aa + bb; + + a.add_assign(&b); + + assert_eq!(FieldPrime::from_bellman(a), cc); + } + } + } diff --git a/zokrates_field/src/lib.rs b/zokrates_field/src/lib.rs index 722bac5b..5b8f2df9 100644 --- a/zokrates_field/src/lib.rs +++ b/zokrates_field/src/lib.rs @@ -1,2 +1 @@ -mod conversion; pub mod field; diff --git a/zokrates_stdlib/stdlib/hashes/sha256/shaRoundNoBoolCheck.code b/zokrates_stdlib/stdlib/hashes/sha256/shaRoundNoBoolCheck.code index a622390c..e02e7312 100644 --- a/zokrates_stdlib/stdlib/hashes/sha256/shaRoundNoBoolCheck.code +++ b/zokrates_stdlib/stdlib/hashes/sha256/shaRoundNoBoolCheck.code @@ -1,4 +1,4 @@ -import "LIBSNARK/sha256round" as sha256 +import "BELLMAN/sha256round" as sha256 // a and b is NOT checked to be of type bool // IV vector is checked to be of type bool def main(field[256] a, field[256] b, field[256] IV) -> (field[256]):