diff --git a/.github/workflows/test-zkvm-miden.yml b/.github/workflows/test-zkvm-miden.yml new file mode 100644 index 0000000..1d68b42 --- /dev/null +++ b/.github/workflows/test-zkvm-miden.yml @@ -0,0 +1,20 @@ +name: Test and clippy Miden + +on: + push: + branches: + - master + pull_request: + +jobs: + test: + uses: ./.github/workflows/test-zkvm.yml + permissions: + contents: read + packages: write + with: + zkvm: miden + toolchain: 1.88.0 + test_ere_dockerized: false + default_features: true + test_options: "" diff --git a/Cargo.lock b/Cargo.lock index 9371f92..efbb053 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -1213,7 +1213,16 @@ version = "3.0.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "8824ecca2e851cec16968d54a01dd372ef8f95b244fb84b84e70128be347c3c6" dependencies = [ - "term", + "term 0.7.0", +] + +[[package]] +name = "ascii-canvas" +version = "4.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ef1e3e699d84ab1b0911a1010c5c106aa34ae89aeac103be5ce0c3859db1e891" +dependencies = [ + "term 1.2.0", ] [[package]] @@ -1800,6 +1809,15 @@ dependencies = [ "windows-targets 0.52.6", ] +[[package]] +name = "backtrace-ext" +version = "0.2.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "537beee3be4a18fb023b570f80e3ae28003db9167a751266b259926e25539d50" +dependencies = [ + "backtrace", +] + [[package]] name = "base16ct" version = "0.2.0" @@ -2324,7 +2342,7 @@ dependencies = [ "serde_json", "syn 2.0.101", "tempfile", - "toml", + "toml 0.8.23", ] [[package]] @@ -2528,7 +2546,7 @@ dependencies = [ "encode_unicode", "libc", "once_cell", - "unicode-width", + "unicode-width 0.2.0", "windows-sys 0.59.0", ] @@ -3280,6 +3298,12 @@ dependencies = [ "syn 2.0.101", ] +[[package]] +name = "dissimilar" +version = "1.0.10" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8975ffdaa0ef3661bfe02dbdcc06c9f829dfafe6a3c474de366a8d5e44276921" + [[package]] name = "docker-generate" version = "0.1.3" @@ -3560,6 +3584,7 @@ dependencies = [ "bincode 1.3.3", "clap", "ere-jolt", + "ere-miden", "ere-nexus", "ere-openvm", "ere-pico", @@ -3604,7 +3629,25 @@ dependencies = [ "tempfile", "test-utils", "thiserror 2.0.12", - "toml", + "toml 0.8.23", + "zkvm-interface", +] + +[[package]] +name = "ere-miden" +version = "0.0.12" +dependencies = [ + "bincode 1.3.3", + "build-utils", + "miden-assembly", + "miden-core", + "miden-processor", + "miden-prover", + "miden-stdlib", + "miden-verifier", + "serde", + "test-utils", + "thiserror 2.0.12", "zkvm-interface", ] @@ -3618,7 +3661,7 @@ dependencies = [ "serde", "test-utils", "thiserror 2.0.12", - "toml", + "toml 0.8.23", "tracing", "zkvm-interface", ] @@ -3639,7 +3682,7 @@ dependencies = [ "serde", "test-utils", "thiserror 2.0.12", - "toml", + "toml 0.8.23", "tracing", "zkvm-interface", ] @@ -3690,7 +3733,7 @@ dependencies = [ "tempfile", "test-utils", "thiserror 2.0.12", - "toml", + "toml 0.8.23", "tracing", "zkvm-interface", ] @@ -3724,7 +3767,7 @@ dependencies = [ "tempfile", "test-utils", "thiserror 2.0.12", - "toml", + "toml 0.8.23", "tracing", "zkvm-interface", ] @@ -3876,7 +3919,7 @@ dependencies = [ "serde", "serde_json", "syn 2.0.101", - "toml", + "toml 0.8.23", "walkdir", ] @@ -4448,6 +4491,20 @@ version = "0.4.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "304de19db7028420975a296ab0fcbbc8e69438c4ed254a1e41e2a7f37d5f0e0a" +[[package]] +name = "generator" +version = "0.8.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "605183a538e3e2a9c1038635cc5c2d194e2ee8fd0d1b66b8349fad7dbacce5a2" +dependencies = [ + "cc", + "cfg-if", + "libc", + "log", + "rustversion", + "windows 0.61.1", +] + [[package]] name = "generic-array" version = "0.14.7" @@ -5372,7 +5429,7 @@ dependencies = [ "console", "number_prefix", "portable-atomic", - "unicode-width", + "unicode-width 0.2.0", "web-time", ] @@ -5421,6 +5478,12 @@ version = "2.11.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "469fb0b9cefa57e3ef31275ee7cacb78f2fdca44e4765491884a2b119d4eb130" +[[package]] +name = "is_ci" +version = "1.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7655c9839580ee829dfacba1d1278c2b7883e50a277ff7541299489d6bdfdc45" + [[package]] name = "is_terminal_polyfill" version = "1.70.1" @@ -5687,21 +5750,42 @@ version = "0.20.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "55cb077ad656299f160924eb2912aa147d7339ea7d69e1b5517326fdcec3c1ca" dependencies = [ - "ascii-canvas", + "ascii-canvas 3.0.0", "bit-set 0.5.3", "ena", "itertools 0.11.0", - "lalrpop-util", - "petgraph", + "lalrpop-util 0.20.2", + "petgraph 0.6.5", "regex", "regex-syntax 0.8.5", "string_cache", - "term", + "term 0.7.0", "tiny-keccak", "unicode-xid", "walkdir", ] +[[package]] +name = "lalrpop" +version = "0.22.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ba4ebbd48ce411c1d10fb35185f5a51a7bfa3d8b24b4e330d30c9e3a34129501" +dependencies = [ + "ascii-canvas 4.0.0", + "bit-set 0.8.0", + "ena", + "itertools 0.14.0", + "lalrpop-util 0.22.2", + "petgraph 0.7.1", + "regex", + "regex-syntax 0.8.5", + "sha3", + "string_cache", + "term 1.2.0", + "unicode-xid", + "walkdir", +] + [[package]] name = "lalrpop-util" version = "0.20.2" @@ -5711,6 +5795,15 @@ dependencies = [ "regex-automata 0.4.9", ] +[[package]] +name = "lalrpop-util" +version = "0.22.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b5baa5e9ff84f1aefd264e6869907646538a52147a755d494517a8007fb48733" +dependencies = [ + "rustversion", +] + [[package]] name = "lazy-regex" version = "3.4.1" @@ -5871,6 +5964,19 @@ version = "0.4.27" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "13dc2df351e3202783a1fe0d44375f7295ffb4049267b0f3018346dc122a1d94" +[[package]] +name = "loom" +version = "0.7.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "419e0dc8046cb947daa77eb95ae174acfbddb7673b4151f56d1eed8e93fbfaca" +dependencies = [ + "cfg-if", + "generator", + "scoped-tls", + "tracing", + "tracing-subscriber 0.3.19", +] + [[package]] name = "lru" version = "0.12.5" @@ -6118,6 +6224,247 @@ dependencies = [ "sketches-ddsketch", ] +[[package]] +name = "miden-air" +version = "0.17.1" +source = "git+https://github.com/0xPolygonMiden/miden-vm.git?tag=v0.17.1#b2effb5d321c72f3cebe761a1399a992e525602c" +dependencies = [ + "miden-core", + "thiserror 2.0.12", + "winter-air", + "winter-prover", +] + +[[package]] +name = "miden-assembly" +version = "0.17.1" +source = "git+https://github.com/0xPolygonMiden/miden-vm.git?tag=v0.17.1#b2effb5d321c72f3cebe761a1399a992e525602c" +dependencies = [ + "log", + "miden-assembly-syntax", + "miden-core", + "miden-mast-package", + "smallvec", + "thiserror 2.0.12", +] + +[[package]] +name = "miden-assembly-syntax" +version = "0.17.1" +source = "git+https://github.com/0xPolygonMiden/miden-vm.git?tag=v0.17.1#b2effb5d321c72f3cebe761a1399a992e525602c" +dependencies = [ + "aho-corasick", + "lalrpop 0.22.2", + "lalrpop-util 0.22.2", + "log", + "miden-core", + "miden-debug-types", + "miden-utils-diagnostics", + "midenc-hir-type", + "regex", + "rustc_version 0.4.1", + "semver 1.0.26", + "smallvec", + "thiserror 2.0.12", +] + +[[package]] +name = "miden-core" +version = "0.17.1" +source = "git+https://github.com/0xPolygonMiden/miden-vm.git?tag=v0.17.1#b2effb5d321c72f3cebe761a1399a992e525602c" +dependencies = [ + "miden-crypto", + "miden-debug-types", + "miden-formatting", + "num-derive", + "num-traits", + "thiserror 2.0.12", + "winter-math", + "winter-utils", +] + +[[package]] +name = "miden-crypto" +version = "0.15.9" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e4329275a11c7d8328b14a7129b21d40183056dcd0d871c3069be6e550d6ca40" +dependencies = [ + "blake3", + "cc", + "glob", + "num", + "num-complex", + "rand 0.9.2", + "rand_core 0.9.3", + "sha3", + "thiserror 2.0.12", + "winter-crypto", + "winter-math", + "winter-utils", +] + +[[package]] +name = "miden-debug-types" +version = "0.17.1" +source = "git+https://github.com/0xPolygonMiden/miden-vm.git?tag=v0.17.1#b2effb5d321c72f3cebe761a1399a992e525602c" +dependencies = [ + "memchr", + "miden-crypto", + "miden-formatting", + "miden-miette", + "miden-utils-sync", + "paste", + "serde", + "serde_spanned 1.0.0", + "thiserror 2.0.12", +] + +[[package]] +name = "miden-formatting" +version = "0.1.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7e392e0a8c34b32671012b439de35fa8987bf14f0f8aac279b97f8b8cc6e263b" +dependencies = [ + "unicode-width 0.1.14", +] + +[[package]] +name = "miden-mast-package" +version = "0.17.1" +source = "git+https://github.com/0xPolygonMiden/miden-vm.git?tag=v0.17.1#b2effb5d321c72f3cebe761a1399a992e525602c" +dependencies = [ + "derive_more 2.0.1", + "miden-assembly-syntax", + "miden-core", +] + +[[package]] +name = "miden-miette" +version = "8.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "eef536978f24a179d94fa2a41e4f92b28e7d8aab14b8d23df28ad2a3d7098b20" +dependencies = [ + "backtrace", + "backtrace-ext", + "cfg-if", + "futures", + "indenter", + "lazy_static", + "miden-miette-derive", + "owo-colors", + "regex", + "rustc_version 0.2.3", + "rustversion", + "serde_json", + "spin 0.9.8", + "strip-ansi-escapes", + "supports-color", + "supports-hyperlinks", + "supports-unicode", + "syn 2.0.101", + "terminal_size", + "textwrap", + "thiserror 2.0.12", + "trybuild", + "unicode-width 0.1.14", +] + +[[package]] +name = "miden-miette-derive" +version = "8.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "86a905f3ea65634dd4d1041a4f0fd0a3e77aa4118341d265af1a94339182222f" +dependencies = [ + "proc-macro2", + "quote", + "syn 2.0.101", +] + +[[package]] +name = "miden-processor" +version = "0.17.1" +source = "git+https://github.com/0xPolygonMiden/miden-vm.git?tag=v0.17.1#b2effb5d321c72f3cebe761a1399a992e525602c" +dependencies = [ + "miden-air", + "miden-core", + "miden-debug-types", + "miden-utils-diagnostics", + "thiserror 2.0.12", + "tracing", + "winter-prover", +] + +[[package]] +name = "miden-prover" +version = "0.17.1" +source = "git+https://github.com/0xPolygonMiden/miden-vm.git?tag=v0.17.1#b2effb5d321c72f3cebe761a1399a992e525602c" +dependencies = [ + "miden-air", + "miden-debug-types", + "miden-processor", + "tracing", + "winter-maybe-async", + "winter-prover", +] + +[[package]] +name = "miden-stdlib" +version = "0.17.1" +source = "git+https://github.com/0xPolygonMiden/miden-vm.git?tag=v0.17.1#b2effb5d321c72f3cebe761a1399a992e525602c" +dependencies = [ + "env_logger", + "miden-assembly", + "miden-core", + "miden-processor", + "miden-utils-sync", + "thiserror 2.0.12", +] + +[[package]] +name = "miden-utils-diagnostics" +version = "0.17.1" +source = "git+https://github.com/0xPolygonMiden/miden-vm.git?tag=v0.17.1#b2effb5d321c72f3cebe761a1399a992e525602c" +dependencies = [ + "miden-crypto", + "miden-debug-types", + "miden-miette", + "paste", + "tracing", +] + +[[package]] +name = "miden-utils-sync" +version = "0.17.1" +source = "git+https://github.com/0xPolygonMiden/miden-vm.git?tag=v0.17.1#b2effb5d321c72f3cebe761a1399a992e525602c" +dependencies = [ + "lock_api", + "loom", + "parking_lot", +] + +[[package]] +name = "miden-verifier" +version = "0.17.1" +source = "git+https://github.com/0xPolygonMiden/miden-vm.git?tag=v0.17.1#b2effb5d321c72f3cebe761a1399a992e525602c" +dependencies = [ + "miden-air", + "miden-core", + "thiserror 2.0.12", + "tracing", + "winter-verifier", +] + +[[package]] +name = "midenc-hir-type" +version = "0.1.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e381ba23e4f57ffa0d6039113f6d6004e5b8c7ae6cb909329b48f2ab525e8680" +dependencies = [ + "miden-formatting", + "smallvec", + "thiserror 2.0.12", +] + [[package]] name = "mime" version = "0.3.17" @@ -7575,7 +7922,7 @@ dependencies = [ "serde_with", "tempfile", "thiserror 1.0.69", - "toml", + "toml 0.8.23", "tracing", ] @@ -7694,7 +8041,7 @@ dependencies = [ "serde", "serde_json", "static_assertions", - "toml", + "toml 0.8.23", "tracing", "tracing-forest", "tracing-subscriber 0.3.19", @@ -7742,6 +8089,12 @@ version = "0.1.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "b15813163c1d831bf4a13c3610c05c0d03b39feb07f7e09fa234dac9b15aaf39" +[[package]] +name = "owo-colors" +version = "4.2.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "48dd4f4a2c8405440fd0462561f0e5806bd0f77e86f51c761481bdd4018b545e" + [[package]] name = "p256" version = "0.13.2" @@ -9202,6 +9555,16 @@ dependencies = [ "indexmap 2.10.0", ] +[[package]] +name = "petgraph" +version = "0.7.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3672b37090dbd86368a4145bc067582552b29c27377cad4e0a306c97f9bd7772" +dependencies = [ + "fixedbitset 0.5.7", + "indexmap 2.10.0", +] + [[package]] name = "pharos" version = "0.5.3" @@ -9704,7 +10067,7 @@ dependencies = [ "lazy_static", "log", "multimap 0.8.3", - "petgraph", + "petgraph 0.6.5", "prettyplease 0.1.25", "prost 0.11.9", "prost-types 0.11.9", @@ -9726,7 +10089,7 @@ dependencies = [ "log", "multimap 0.10.1", "once_cell", - "petgraph", + "petgraph 0.6.5", "prettyplease 0.2.32", "prost 0.12.6", "prost-types 0.12.6", @@ -10842,6 +11205,15 @@ version = "2.1.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "3e75f6a532d0fd9f7f13144f392b6ad56a32696bfcd9c78f797f16bbb6f072d6" +[[package]] +name = "rustc_version" +version = "0.2.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "138e3e0acb6c9fb258b19b67cb8abd63c00679d2851805ea151465464fe9030a" +dependencies = [ + "semver 0.9.0", +] + [[package]] name = "rustc_version" version = "0.3.3" @@ -11048,7 +11420,7 @@ dependencies = [ "strum 0.27.2", "tempfile", "thiserror 2.0.12", - "toml", + "toml 0.8.23", "yaml-rust2", ] @@ -11121,6 +11493,12 @@ dependencies = [ "windows-sys 0.59.0", ] +[[package]] +name = "scoped-tls" +version = "1.0.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e1cf6437eb19a8f4a6cc0f7dca544973b0b78843adbfeb3683d1a94a0024a294" + [[package]] name = "scopeguard" version = "1.2.0" @@ -11227,13 +11605,22 @@ dependencies = [ "libc", ] +[[package]] +name = "semver" +version = "0.9.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1d7eb9ef2c18661902cc47e535f9bc51b78acd254da71d375c2f6720d9a40403" +dependencies = [ + "semver-parser 0.7.0", +] + [[package]] name = "semver" version = "0.11.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "f301af10236f6df4160f7c3f04eec6dbc70ace82d23326abad5edee88801c6b6" dependencies = [ - "semver-parser", + "semver-parser 0.10.3", ] [[package]] @@ -11245,6 +11632,12 @@ dependencies = [ "serde", ] +[[package]] +name = "semver-parser" +version = "0.7.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "388a1df253eca08550bef6c72392cfe7c30914bf41df5269b68cbd6ff8f570a3" + [[package]] name = "semver-parser" version = "0.10.3" @@ -11344,6 +11737,15 @@ dependencies = [ "serde", ] +[[package]] +name = "serde_spanned" +version = "1.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "40734c41988f7306bb04f0ecf60ec0f3f1caa34290e4e8ea471dcd3346483b83" +dependencies = [ + "serde", +] + [[package]] name = "serde_urlencoded" version = "0.7.1" @@ -11551,6 +11953,12 @@ dependencies = [ "serde", ] +[[package]] +name = "smawk" +version = "0.3.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b7c388c1b5e93756d0c740965c41e8822f866621d41acbdf6336a6a168f8840c" + [[package]] name = "snowbridge-amcl" version = "1.0.2" @@ -11578,8 +11986,8 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "c425ce1c59f4b154717592f0bdf4715c3a1d55058883622d3157e1f0908a5b26" dependencies = [ "itertools 0.11.0", - "lalrpop", - "lalrpop-util", + "lalrpop 0.20.2", + "lalrpop-util 0.20.2", "phf", "thiserror 1.0.69", "unicode-xid", @@ -12151,6 +12559,15 @@ dependencies = [ "precomputed-hash", ] +[[package]] +name = "strip-ansi-escapes" +version = "0.2.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2a8f8038e7e7969abb3f1b7c2a811225e9296da208539e0f79c5251d6cac0025" +dependencies = [ + "vte", +] + [[package]] name = "strsim" version = "0.11.1" @@ -12239,6 +12656,27 @@ version = "2.6.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "13c2bddecc57b384dee18652358fb23172facb8a2c51ccc10d74c157bdea3292" +[[package]] +name = "supports-color" +version = "3.0.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c64fc7232dd8d2e4ac5ce4ef302b1d81e0b80d055b9d77c7c4f51f6aa4c867d6" +dependencies = [ + "is_ci", +] + +[[package]] +name = "supports-hyperlinks" +version = "3.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "804f44ed3c63152de6a9f90acbea1a110441de43006ea51bcce8f436196a288b" + +[[package]] +name = "supports-unicode" +version = "3.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b7401a30af6cb5818bb64852270bb722533397edcfc7344954a38f420819ece2" + [[package]] name = "svm-rs" version = "0.3.5" @@ -12376,7 +12814,7 @@ dependencies = [ "ntapi", "once_cell", "rayon", - "windows", + "windows 0.52.0", ] [[package]] @@ -12433,6 +12871,12 @@ version = "0.12.16" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "61c41af27dd6d1e27b1b16b489db798443478cef1f06a660c96db617ba5de3b1" +[[package]] +name = "target-triple" +version = "0.1.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1ac9aa371f599d22256307c24a9d748c041e548cbf599f35d890f9d365361790" + [[package]] name = "tempfile" version = "3.20.0" @@ -12457,6 +12901,34 @@ dependencies = [ "winapi", ] +[[package]] +name = "term" +version = "1.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "2111ef44dae28680ae9752bb89409e7310ca33a8c621ebe7b106cf5c928b3ac0" +dependencies = [ + "windows-sys 0.59.0", +] + +[[package]] +name = "termcolor" +version = "1.4.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "06794f8f6c5c898b3275aebefa6b8a1cb24cd2c6c79397ab15774837a0bc5755" +dependencies = [ + "winapi-util", +] + +[[package]] +name = "terminal_size" +version = "0.3.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "21bebf2b7c9e0a515f6e0f8c51dc0f8e4696391e6f1ff30379559f8365fb0df7" +dependencies = [ + "rustix 0.38.44", + "windows-sys 0.48.0", +] + [[package]] name = "test-utils" version = "0.0.12" @@ -12468,6 +12940,17 @@ dependencies = [ "zkvm-interface", ] +[[package]] +name = "textwrap" +version = "0.16.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c13547615a44dc9c452a8a534638acdf07120d4b6847c8178705da06306a3057" +dependencies = [ + "smawk", + "unicode-linebreak", + "unicode-width 0.2.0", +] + [[package]] name = "thiserror" version = "1.0.69" @@ -12740,11 +13223,26 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "dc1beb996b9d83529a9e75c17a1686767d148d70663143c7854d8b4a09ced362" dependencies = [ "serde", - "serde_spanned", - "toml_datetime", + "serde_spanned 0.6.9", + "toml_datetime 0.6.11", "toml_edit 0.22.27", ] +[[package]] +name = "toml" +version = "0.9.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "75129e1dc5000bfbaa9fee9d1b21f974f9fbad9daec557a521ee6e080825f6e8" +dependencies = [ + "indexmap 2.10.0", + "serde", + "serde_spanned 1.0.0", + "toml_datetime 0.7.0", + "toml_parser", + "toml_writer", + "winnow 0.7.10", +] + [[package]] name = "toml_datetime" version = "0.6.11" @@ -12754,6 +13252,15 @@ dependencies = [ "serde", ] +[[package]] +name = "toml_datetime" +version = "0.7.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bade1c3e902f58d73d3f294cd7f20391c1cb2fbcb643b73566bc773971df91e3" +dependencies = [ + "serde", +] + [[package]] name = "toml_edit" version = "0.19.15" @@ -12761,7 +13268,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "1b5bb770da30e5cbfde35a2d7b9b8a2c4b8ef89548a7a6aeab5c9a576e3e7421" dependencies = [ "indexmap 2.10.0", - "toml_datetime", + "toml_datetime 0.6.11", "winnow 0.5.40", ] @@ -12773,18 +13280,33 @@ checksum = "41fe8c660ae4257887cf66394862d21dbca4a6ddd26f04a3560410406a2f819a" dependencies = [ "indexmap 2.10.0", "serde", - "serde_spanned", - "toml_datetime", + "serde_spanned 0.6.9", + "toml_datetime 0.6.11", "toml_write", "winnow 0.7.10", ] +[[package]] +name = "toml_parser" +version = "1.0.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b551886f449aa90d4fe2bdaa9f4a2577ad2dde302c61ecf262d80b116db95c10" +dependencies = [ + "winnow 0.7.10", +] + [[package]] name = "toml_write" version = "0.1.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "5d99f8c9a7727884afe522e9bd5edbfc91a3312b36a77b5fb8926e4c31a41801" +[[package]] +name = "toml_writer" +version = "1.0.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "fcc842091f2def52017664b53082ecbbeb5c7731092bad69d2c63050401dfd64" + [[package]] name = "tonic" version = "0.8.3" @@ -13081,6 +13603,22 @@ version = "0.2.5" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "e421abadd41a4225275504ea4d6566923418b7f05506fbc9c0fe86ba7396114b" +[[package]] +name = "trybuild" +version = "1.0.111" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0ded9fdb81f30a5708920310bfcd9ea7482ff9cba5f54601f7a19a877d5c2392" +dependencies = [ + "dissimilar", + "glob", + "serde", + "serde_derive", + "serde_json", + "target-triple", + "termcolor", + "toml 0.9.5", +] + [[package]] name = "tungstenite" version = "0.20.1" @@ -13205,12 +13743,24 @@ version = "1.0.18" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "5a5f39404a5da50712a4c1eecf25e90dd62b613502b7e925fd4e4d19b5c96512" +[[package]] +name = "unicode-linebreak" +version = "0.1.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3b09c83c3c29d37506a3e260c08c03743a6bb66a9cd432c6934ab501a190571f" + [[package]] name = "unicode-segmentation" version = "1.12.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "f6ccf251212114b54433ec949fd6a7841275f9ada20dddd2f29e9ceea4501493" +[[package]] +name = "unicode-width" +version = "0.1.14" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7dd6e30e90baa6f72411720665d41d89b9a3d039dc45b8faea1ddd07f617f6af" + [[package]] name = "unicode-width" version = "0.2.0" @@ -13383,6 +13933,15 @@ version = "0.8.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "5c3082ca00d5a5ef149bb8b555a72ae84c9c59f7250f013ac822ac2e49b19c64" +[[package]] +name = "vte" +version = "0.14.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "231fdcd7ef3037e8330d8e17e61011a2c244126acc0a982f4040ac3f9f0bc077" +dependencies = [ + "memchr", +] + [[package]] name = "wait-timeout" version = "0.2.1" @@ -13639,6 +14198,28 @@ dependencies = [ "windows-targets 0.52.6", ] +[[package]] +name = "windows" +version = "0.61.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c5ee8f3d025738cb02bad7868bbb5f8a6327501e870bf51f1b455b0a2454a419" +dependencies = [ + "windows-collections", + "windows-core 0.61.0", + "windows-future", + "windows-link", + "windows-numerics", +] + +[[package]] +name = "windows-collections" +version = "0.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3beeceb5e5cfd9eb1d76b381630e82c4241ccd0d27f1a39ed41b2760b255c5e8" +dependencies = [ + "windows-core 0.61.0", +] + [[package]] name = "windows-core" version = "0.52.0" @@ -13661,6 +14242,16 @@ dependencies = [ "windows-strings 0.4.0", ] +[[package]] +name = "windows-future" +version = "0.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7a1d6bbefcb7b60acd19828e1bc965da6fcf18a7e39490c5f8be71e54a19ba32" +dependencies = [ + "windows-core 0.61.0", + "windows-link", +] + [[package]] name = "windows-implement" version = "0.60.0" @@ -13689,6 +14280,16 @@ version = "0.1.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "76840935b766e1b0a05c0066835fb9ec80071d4c09a16f6bd5f7e655e3c14c38" +[[package]] +name = "windows-numerics" +version = "0.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9150af68066c4c5c07ddc0ce30421554771e528bde427614c61038bc2c92c2b1" +dependencies = [ + "windows-core 0.61.0", + "windows-link", +] + [[package]] name = "windows-registry" version = "0.4.0" @@ -13967,6 +14568,95 @@ dependencies = [ "windows-sys 0.48.0", ] +[[package]] +name = "winter-air" +version = "0.13.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "ef01227f23c7c331710f43b877a8333f5f8d539631eea763600f1a74bf018c7c" +dependencies = [ + "libm", + "winter-crypto", + "winter-fri", + "winter-math", + "winter-utils", +] + +[[package]] +name = "winter-crypto" +version = "0.13.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1cdb247bc142438798edb04067ab72a22cf815f57abbd7b78a6fa986fc101db8" +dependencies = [ + "blake3", + "sha3", + "winter-math", + "winter-utils", +] + +[[package]] +name = "winter-fri" +version = "0.13.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "fd592b943f9d65545683868aaf1b601eb66e52bfd67175347362efff09101d3a" +dependencies = [ + "winter-crypto", + "winter-math", + "winter-utils", +] + +[[package]] +name = "winter-math" +version = "0.13.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7aecfb48ee6a8b4746392c8ff31e33e62df8528a3b5628c5af27b92b14aef1ea" +dependencies = [ + "winter-utils", +] + +[[package]] +name = "winter-maybe-async" +version = "0.13.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6d31a19dae58475d019850e25b0170e94b16d382fbf6afee9c0e80fdc935e73e" +dependencies = [ + "quote", + "syn 2.0.101", +] + +[[package]] +name = "winter-prover" +version = "0.13.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "84cc631ed56cd39b78ef932c1ec4060cc6a44d114474291216c32f56655b3048" +dependencies = [ + "tracing", + "winter-air", + "winter-crypto", + "winter-fri", + "winter-math", + "winter-maybe-async", + "winter-utils", +] + +[[package]] +name = "winter-utils" +version = "0.13.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9951263ef5317740cd0f49e618db00c72fabb70b75756ea26c4d5efe462c04dd" + +[[package]] +name = "winter-verifier" +version = "0.13.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0425ea81f8f703a1021810216da12003175c7974a584660856224df04b2e2fdb" +dependencies = [ + "winter-air", + "winter-crypto", + "winter-fri", + "winter-math", + "winter-utils", +] + [[package]] name = "wit-bindgen-rt" version = "0.39.0" diff --git a/Cargo.toml b/Cargo.toml index 453863d..4e83055 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -4,6 +4,7 @@ members = [ "crates/test-utils", # zkVMs "crates/ere-jolt", + "crates/ere-miden", "crates/ere-nexus", "crates/ere-openvm", "crates/ere-pico", @@ -57,6 +58,14 @@ jolt = { git = "https://github.com/a16z/jolt.git", rev = "55b9830a3944dde55d33a5 jolt-core = { git = "https://github.com/a16z/jolt.git", rev = "55b9830a3944dde55d33a55c42522b81dd49f87a" } jolt-sdk = { git = "https://github.com/a16z/jolt.git", rev = "55b9830a3944dde55d33a55c42522b81dd49f87a" } +# Miden dependencies +miden-assembly = { git = "https://github.com/0xPolygonMiden/miden-vm.git", tag = "v0.17.1" } +miden-core = { git = "https://github.com/0xPolygonMiden/miden-vm.git", tag = "v0.17.1" } +miden-processor = { git = "https://github.com/0xPolygonMiden/miden-vm.git", tag = "v0.17.1" } +miden-prover = { git = "https://github.com/0xPolygonMiden/miden-vm.git", tag = "v0.17.1" } +miden-stdlib = { git = "https://github.com/0xPolygonMiden/miden-vm.git", tag = "v0.17.1" } +miden-verifier = { git = "https://github.com/0xPolygonMiden/miden-vm.git", tag = "v0.17.1" } + # Nexus dependencies nexus-sdk = { git = "https://github.com/nexus-xyz/nexus-zkvm.git", tag = "v0.3.4" } @@ -90,6 +99,7 @@ test-utils = { path = "crates/test-utils" } ere-cli = { path = "crates/ere-cli", default-features = false } ere-dockerized = { path = "crates/ere-dockerized" } ere-jolt = { path = "crates/ere-jolt", default-features = false } +ere-miden = { path = "crates/ere-miden", default-features = false } ere-nexus = { path = "crates/ere-nexus", default-features = false } ere-openvm = { path = "crates/ere-openvm", default-features = false } ere-pico = { path = "crates/ere-pico", default-features = false } diff --git a/README.md b/README.md index 5b37498..081825e 100644 --- a/README.md +++ b/README.md @@ -45,6 +45,7 @@ - Pico - Zisk - Nexus +- Miden ## Quick Start diff --git a/crates/ere-cli/Cargo.toml b/crates/ere-cli/Cargo.toml index afd38f2..87f22ed 100644 --- a/crates/ere-cli/Cargo.toml +++ b/crates/ere-cli/Cargo.toml @@ -14,6 +14,7 @@ tracing-subscriber = { workspace = true, features = ["env-filter"], optional = t # Local dependencies ere-jolt = { workspace = true, optional = true } +ere-miden = { workspace = true, optional = true } ere-nexus = { workspace = true, optional = true } ere-openvm = { workspace = true, optional = true } ere-pico = { workspace = true, optional = true } @@ -34,6 +35,7 @@ cli = ["dep:clap", "dep:tracing-subscriber"] # zkVM jolt = ["dep:ere-jolt"] +miden = ["dep:ere-miden"] nexus = ["dep:ere-nexus"] openvm = ["dep:ere-openvm"] pico = ["dep:ere-pico"] diff --git a/crates/ere-cli/src/main.rs b/crates/ere-cli/src/main.rs index e16b997..52936d5 100644 --- a/crates/ere-cli/src/main.rs +++ b/crates/ere-cli/src/main.rs @@ -10,6 +10,7 @@ const _: () = { if cfg!(feature = "cli") { assert!( (cfg!(feature = "jolt") as u8 + + cfg!(feature = "miden") as u8 + cfg!(feature = "nexus") as u8 + cfg!(feature = "openvm") as u8 + cfg!(feature = "pico") as u8 @@ -136,6 +137,9 @@ fn compile(guest_path: PathBuf, program_path: PathBuf) -> Result<(), Error> { #[cfg(feature = "jolt")] let program = ere_jolt::JOLT_TARGET.compile(&guest_path); + #[cfg(feature = "miden")] + let program = ere_miden::MIDEN_TARGET.compile(&guest_path); + #[cfg(feature = "nexus")] let program = ere_nexus::NEXUS_TARGET.compile(&guest_path); @@ -232,6 +236,9 @@ fn construct_zkvm(program_path: PathBuf, resource: ProverResourceType) -> Result #[cfg(feature = "jolt")] let zkvm = ere_jolt::EreJolt::new(program, resource); + #[cfg(feature = "miden")] + let zkvm = ere_miden::EreMiden::new(program, resource); + #[cfg(feature = "nexus")] let zkvm = Ok::<_, Error>(ere_nexus::EreNexus::new(program, resource)); diff --git a/crates/ere-miden/Cargo.toml b/crates/ere-miden/Cargo.toml new file mode 100644 index 0000000..21868f4 --- /dev/null +++ b/crates/ere-miden/Cargo.toml @@ -0,0 +1,29 @@ +[package] +name = "ere-miden" +version.workspace = true +edition.workspace = true +rust-version.workspace = true +license.workspace = true + +[dependencies] +bincode = { workspace = true } +serde = { workspace = true, features = ["derive"] } +thiserror = { workspace = true } +zkvm-interface = { workspace = true } + +# Miden +miden-assembly = { workspace = true, features = ["std"] } +miden-core = { workspace = true, features = ["std"] } +miden-processor = { workspace = true, features = ["std"] } +miden-prover = { workspace = true, features = ["std"] } +miden-stdlib = { workspace = true, features = ["std"] } +miden-verifier = { workspace = true } + +[dev-dependencies] +test-utils = { workspace = true, features = ["host"] } + +[build-dependencies] +build-utils.workspace = true + +[lints] +workspace = true diff --git a/crates/ere-miden/build.rs b/crates/ere-miden/build.rs new file mode 100644 index 0000000..ebfcc35 --- /dev/null +++ b/crates/ere-miden/build.rs @@ -0,0 +1,5 @@ +use build_utils::detect_and_generate_name_and_sdk_version; + +fn main() { + detect_and_generate_name_and_sdk_version("miden", "miden-core"); +} diff --git a/crates/ere-miden/src/compile.rs b/crates/ere-miden/src/compile.rs new file mode 100644 index 0000000..cef1731 --- /dev/null +++ b/crates/ere-miden/src/compile.rs @@ -0,0 +1,64 @@ +use crate::{ + MIDEN_TARGET, MidenProgram, + error::{CompileError, MidenError}, +}; +use miden_assembly::Assembler; +use miden_core::utils::Serializable; +use miden_stdlib::StdLibrary; +use std::{fs, path::Path}; +use zkvm_interface::Compiler; + +impl Compiler for MIDEN_TARGET { + type Error = MidenError; + type Program = MidenProgram; + + fn compile(&self, guest_directory: &Path) -> Result { + let dir_name = guest_directory + .file_name() + .and_then(|name| name.to_str()) + .ok_or(CompileError::InvalidProgramPath)?; + + let entrypoint = format!("{dir_name}.masm"); + let main_path = guest_directory.join(&entrypoint); + if !main_path.exists() { + return Err(CompileError::MissingEntrypoint { + program_dir: guest_directory.display().to_string(), + entrypoint, + } + .into()); + } + + // Compile using Miden assembler + let mut assembler = Assembler::default().with_debug_mode(true); + assembler + .link_dynamic_library(StdLibrary::default()) + .map_err(|e| CompileError::LoadStdLibrary(e.to_string()))?; + + let source = fs::read_to_string(&main_path).map_err(|e| CompileError::ReadSource { + path: main_path.clone(), + source: e, + })?; + + let program = assembler + .assemble_program(&source) + .map_err(|e| CompileError::AssemblyCompilation(e.to_string()))?; + + Ok(MidenProgram { + program_bytes: program.to_bytes(), + }) + } +} + +#[cfg(test)] +mod tests { + use super::*; + use test_utils::host::testing_guest_directory; + use zkvm_interface::Compiler; + + #[test] + fn test_compile() { + let guest_directory = testing_guest_directory("miden", "fib"); + let program = MIDEN_TARGET.compile(&guest_directory).unwrap(); + assert!(!program.program_bytes.is_empty()); + } +} diff --git a/crates/ere-miden/src/error.rs b/crates/ere-miden/src/error.rs new file mode 100644 index 0000000..3225f0c --- /dev/null +++ b/crates/ere-miden/src/error.rs @@ -0,0 +1,77 @@ +use miden_core::utils::DeserializationError; +use miden_processor::ExecutionError; +use miden_verifier::VerificationError; +use std::path::PathBuf; +use thiserror::Error; +use zkvm_interface::zkVMError; + +impl From for zkVMError { + fn from(value: MidenError) -> Self { + zkVMError::Other(Box::new(value)) + } +} + +#[derive(Debug, Error)] +pub enum MidenError { + #[error(transparent)] + Compile(#[from] CompileError), + #[error(transparent)] + Execute(#[from] ExecuteError), + #[error(transparent)] + Prove(#[from] ProveError), + #[error(transparent)] + Verify(#[from] VerifyError), +} + +#[derive(Debug, Error)] +pub enum CompileError { + #[error("Invalid program directory name")] + InvalidProgramPath, + #[error("Entrypoint '{entrypoint}' not found in {program_dir}")] + MissingEntrypoint { + program_dir: String, + entrypoint: String, + }, + #[error("Failed to read assembly source at {path}")] + ReadSource { + path: PathBuf, + #[source] + source: std::io::Error, + }, + #[error("Miden assembly compilation failed: {0}")] + AssemblyCompilation(String), + #[error("Failed to load Miden standard library: {0}")] + LoadStdLibrary(String), +} + +#[derive(Debug, Error)] +pub enum ExecuteError { + #[error("Miden execution failed")] + Execution(#[from] ExecutionError), + #[error("Invalid input format: {0}")] + InvalidInput(String), + #[error("Serialization failed")] + Serialization(#[from] bincode::Error), + #[error("Failed to deserialize Miden program")] + ProgramDeserialization(#[from] DeserializationError), +} + +#[derive(Debug, Error)] +pub enum ProveError { + #[error("Miden proving failed")] + Proving(#[from] ExecutionError), + #[error("Invalid input format: {0}")] + InvalidInput(String), + #[error("Serialization failed")] + Serialization(#[from] bincode::Error), +} + +#[derive(Debug, Error)] +pub enum VerifyError { + #[error("Miden verification failed")] + Verification(#[from] VerificationError), + #[error("Proof or associated data deserialization failed")] + MidenDeserialization(#[from] DeserializationError), + #[error("Proof bundle deserialization failed")] + BundleDeserialization(#[from] bincode::Error), +} diff --git a/crates/ere-miden/src/io.rs b/crates/ere-miden/src/io.rs new file mode 100644 index 0000000..a853fff --- /dev/null +++ b/crates/ere-miden/src/io.rs @@ -0,0 +1,52 @@ +use crate::error::{ExecuteError, MidenError}; +use miden_processor::{AdviceInputs, StackInputs, StackOutputs}; +use zkvm_interface::{Input, InputItem, PublicValues}; + +/// Returns Miden compatible inputs from `zkvm_interface::Input`. +/// +/// All inputs are serialized and concatenated, then placed onto the advice tape. +/// The stack is left empty. +pub fn generate_miden_inputs(inputs: &Input) -> Result<(StackInputs, AdviceInputs), MidenError> { + let mut all_bytes = Vec::new(); + + for item in inputs.iter() { + match item { + InputItem::Object(obj) => { + bincode::serialize_into(&mut all_bytes, &**obj) + .map_err(ExecuteError::Serialization)?; + } + InputItem::SerializedObject(bytes) | InputItem::Bytes(bytes) => { + all_bytes.extend_from_slice(bytes); + } + } + } + + // Convert the byte stream into u64 words for the Miden VM. + let advice_words: Vec = { + let mut words: Vec = all_bytes + .chunks_exact(8) + .map(|chunk| u64::from_le_bytes(chunk.try_into().unwrap())) + .collect(); + + let remainder = all_bytes.chunks_exact(8).remainder(); + if !remainder.is_empty() { + let mut last_chunk = [0u8; 8]; + last_chunk[..remainder.len()].copy_from_slice(remainder); + words.push(u64::from_le_bytes(last_chunk)); + } + + words + }; + + let advice_inputs = AdviceInputs::default() + .with_stack_values(advice_words) + .map_err(|e| ExecuteError::InvalidInput(e.to_string()))?; + + Ok((StackInputs::default(), advice_inputs)) +} + +// Convert Miden stack outputs to public values +pub fn outputs_to_public_values(outputs: &StackOutputs) -> Result { + let output_ints: Vec = outputs.iter().map(|f| f.as_int()).collect(); + bincode::serialize(&output_ints) +} diff --git a/crates/ere-miden/src/lib.rs b/crates/ere-miden/src/lib.rs new file mode 100644 index 0000000..064d85f --- /dev/null +++ b/crates/ere-miden/src/lib.rs @@ -0,0 +1,245 @@ +pub mod compile; +pub mod error; +pub mod io; + +use self::error::{ExecuteError, MidenError, VerifyError}; +use self::io::{generate_miden_inputs, outputs_to_public_values}; +use miden_core::{ + Program, + utils::{Deserializable, Serializable}, +}; +use miden_processor::{ + DefaultHost, ExecutionOptions, ProgramInfo, StackInputs, StackOutputs, execute as miden_execute, +}; +use miden_prover::{ExecutionProof, ProvingOptions, prove as miden_prove}; +use miden_stdlib::StdLibrary; +use miden_verifier::verify as miden_verify; +use serde::{Deserialize, Serialize, de::DeserializeOwned}; +use std::{env, io::Read, time::Instant}; +use zkvm_interface::{ + Input, ProgramExecutionReport, ProgramProvingReport, Proof, ProverResourceType, PublicValues, + zkVM, zkVMError, +}; + +include!(concat!(env!("OUT_DIR"), "/name_and_sdk_version.rs")); + +#[allow(non_camel_case_types)] +pub struct MIDEN_TARGET; + +#[derive(Clone, Serialize, Deserialize)] +pub struct MidenProgram { + pub program_bytes: Vec, +} + +#[derive(Serialize, Deserialize)] +struct MidenProofBundle { + stack_inputs: Vec, + stack_outputs: Vec, + proof: Vec, +} + +pub struct EreMiden { + program: Program, +} + +impl EreMiden { + pub fn new(program: MidenProgram, _resource: ProverResourceType) -> Result { + let program = Program::read_from_bytes(&program.program_bytes) + .map_err(ExecuteError::ProgramDeserialization) + .map_err(MidenError::Execute)?; + + Ok(Self { program }) + } + + fn setup_host() -> Result { + let mut host = DefaultHost::default(); + + host.load_library(&StdLibrary::default()) + .map_err(ExecuteError::Execution) + .map_err(MidenError::Execute)?; + + Ok(host) + } +} + +impl zkVM for EreMiden { + fn execute(&self, inputs: &Input) -> Result<(PublicValues, ProgramExecutionReport), zkVMError> { + let (stack_inputs, advice_inputs) = generate_miden_inputs(inputs)?; + let mut host = Self::setup_host()?; + + let start = Instant::now(); + let trace = miden_execute( + &self.program, + stack_inputs, + advice_inputs, + &mut host, + ExecutionOptions::default(), + ) + .map_err(|e| MidenError::Execute(e.into()))?; + + let public_values = outputs_to_public_values(trace.stack_outputs()) + .map_err(|e| MidenError::Execute(e.into()))?; + + let report = ProgramExecutionReport { + total_num_cycles: trace.trace_len_summary().main_trace_len() as u64, + execution_duration: start.elapsed(), + ..Default::default() + }; + + Ok((public_values, report)) + } + + fn prove( + &self, + inputs: &Input, + ) -> Result<(PublicValues, Proof, ProgramProvingReport), zkVMError> { + let (stack_inputs, advice_inputs) = generate_miden_inputs(inputs)?; + let mut host = Self::setup_host()?; + + let start = Instant::now(); + let proving_options = ProvingOptions::with_96_bit_security(env::var("MIDEN_DEBUG").is_ok()); + + let (stack_outputs, proof) = miden_prove( + &self.program, + stack_inputs.clone(), + advice_inputs, + &mut host, + proving_options, + ) + .map_err(|e| MidenError::Prove(e.into()))?; + + let public_values = + outputs_to_public_values(&stack_outputs).map_err(|e| MidenError::Prove(e.into()))?; + + let bundle = MidenProofBundle { + stack_inputs: stack_inputs.to_bytes(), + stack_outputs: stack_outputs.to_bytes(), + proof: proof.to_bytes(), + }; + + let proof_bytes = bincode::serialize(&bundle).map_err(|e| MidenError::Prove(e.into()))?; + + Ok(( + public_values, + proof_bytes, + ProgramProvingReport::new(start.elapsed()), + )) + } + + fn verify(&self, proof: &[u8]) -> Result { + let bundle: MidenProofBundle = bincode::deserialize(proof) + .map_err(|e| MidenError::Verify(VerifyError::BundleDeserialization(e)))?; + + let program_info: ProgramInfo = self.program.clone().into(); + + let stack_inputs = StackInputs::read_from_bytes(&bundle.stack_inputs) + .map_err(|e| MidenError::Verify(VerifyError::MidenDeserialization(e)))?; + let stack_outputs = StackOutputs::read_from_bytes(&bundle.stack_outputs) + .map_err(|e| MidenError::Verify(VerifyError::MidenDeserialization(e)))?; + let execution_proof = ExecutionProof::from_bytes(&bundle.proof) + .map_err(|e| MidenError::Verify(VerifyError::MidenDeserialization(e)))?; + + miden_verify( + program_info, + stack_inputs, + stack_outputs.clone(), + execution_proof, + ) + .map_err(|e| MidenError::Verify(e.into()))?; + + Ok(outputs_to_public_values(&stack_outputs) + .map_err(|e| MidenError::Verify(VerifyError::BundleDeserialization(e)))?) + } + + fn deserialize_from(&self, reader: R) -> Result { + bincode::deserialize_from(reader).map_err(|e| MidenError::Execute(e.into()).into()) + } + + fn name(&self) -> &'static str { + NAME + } + + fn sdk_version(&self) -> &'static str { + SDK_VERSION + } +} + +#[cfg(test)] +mod tests { + use super::*; + use test_utils::host::testing_guest_directory; + use zkvm_interface::Compiler; + + fn load_miden_program(guest_name: &str) -> MidenProgram { + MIDEN_TARGET + .compile(&testing_guest_directory("miden", guest_name)) + .unwrap() + } + + #[test] + fn test_prove_and_verify_add() { + let program = load_miden_program("add"); + let zkvm = EreMiden::new(program, ProverResourceType::Cpu).unwrap(); + + let const_a = 2518446814u64; + let const_b = 1949327098u64; + let expected_sum = const_a + const_b; + + let mut inputs = Input::new(); + inputs.write(const_a); + inputs.write(const_b); + + // Prove + let (prover_public_values, proof, _) = zkvm.prove(&inputs).unwrap(); + + // Verify + let verifier_public_values = zkvm.verify(&proof).unwrap(); + assert_eq!(prover_public_values, verifier_public_values,); + + // Assert output + let output: Vec = zkvm + .deserialize_from(verifier_public_values.as_slice()) + .unwrap(); + assert_eq!(output[0], expected_sum); + } + + #[test] + fn test_prove_and_verify_fib() { + let program = load_miden_program("fib"); + let zkvm = EreMiden::new(program, ProverResourceType::Cpu).unwrap(); + + let n_iterations = 50u64; + let expected_fib = 12_586_269_025u64; + + let mut inputs = Input::new(); + inputs.write(0u64); + inputs.write(1u64); + inputs.write(n_iterations); + + // Prove + let (prover_public_values, proof, _) = zkvm.prove(&inputs).unwrap(); + + // Verify + let verifier_public_values = zkvm.verify(&proof).unwrap(); + assert_eq!(prover_public_values, verifier_public_values,); + + // Assert output + let output: Vec = zkvm + .deserialize_from(verifier_public_values.as_slice()) + .unwrap(); + assert_eq!(output[0], expected_fib); + } + + #[test] + fn test_invalid_inputs() { + let program = load_miden_program("add"); + let zkvm = EreMiden::new(program, ProverResourceType::Cpu).unwrap(); + + let empty_inputs = Input::new(); + assert!(zkvm.execute(&empty_inputs).is_err()); + + let mut insufficient_inputs = Input::new(); + insufficient_inputs.write(5u64); + assert!(zkvm.execute(&insufficient_inputs).is_err()); + } +} diff --git a/docker/miden/Dockerfile b/docker/miden/Dockerfile new file mode 100644 index 0000000..17dbf4f --- /dev/null +++ b/docker/miden/Dockerfile @@ -0,0 +1,19 @@ +ARG BASE_IMAGE_TAG=ere-base:latest + +FROM ${BASE_IMAGE_TAG} + +# Set default toolchain to MSRV of Miden +RUN rustup default 1.88.0 + +# Miden Configuration +ENV MIDEN_VERSION="v0.17.1" \ + MIDEN_TOOLCHAIN_VERSION="1.88.0" + +# Miden CLI Installation +# COPY --chmod=755 scripts/sdk_installers/install_miden_sdk.sh /tmp/ +# RUN /tmp/install_miden_sdk.sh && rm /tmp/install_miden_sdk.sh + +# Verify +# RUN miden-vm --version + +CMD ["/bin/bash"] diff --git a/tests/miden/add/add.masm b/tests/miden/add/add.masm new file mode 100644 index 0000000..bb010b1 --- /dev/null +++ b/tests/miden/add/add.masm @@ -0,0 +1,12 @@ +# Adds two numbers from advice stack +# Input: advice_stack contains second_number, first_number +use.std::sys + +begin + adv_push.1 + adv_push.1 + + add + + exec.sys::truncate_stack +end diff --git a/tests/miden/fib/fib.masm b/tests/miden/fib/fib.masm new file mode 100644 index 0000000..6f489d4 --- /dev/null +++ b/tests/miden/fib/fib.masm @@ -0,0 +1,29 @@ +# Fibonacci +# Reads three u64 values from advice stack: fib_a, fib_b, n +# Returns nth fibonacci number +use.std::sys + +begin + # Read inputs from advice stack + adv_push.1 # fib_a + adv_push.1 # fib_b + adv_push.1 # n + + # Compute fibonacci + dup neq.0 + while.true + movdn.2 + dup.1 + add + swap + movup.2 + sub.1 + dup neq.0 + end + + # Drop counter and one of the fibonacci values + drop + drop + + exec.sys::truncate_stack +end