merge master

This commit is contained in:
gluaxspeed 2021-08-18 02:10:59 -07:00
commit e6948da23f
163 changed files with 1569 additions and 922 deletions

View File

@ -5,7 +5,7 @@ commands:
parameters:
cache_key:
type: string
default: leo-stable-cache
default: leo-stable-linux-cache
steps:
- run: set -e
- setup_remote_docker
@ -31,7 +31,7 @@ commands:
parameters:
cache_key:
type: string
default: leo-stable-cache
default: leo-stable-linux-cache
steps:
- run: (sccache -s||true)
- run: set +e
@ -40,25 +40,81 @@ commands:
paths:
- .cache/sccache
- .cargo
jobs:
# orbs:
# codecov: codecov/codecov@1.2.3
rust-stable:
jobs:
check-style:
docker:
- image: cimg/rust:1.53
resource_class: xlarge
steps:
- checkout
- setup_environment:
cache_key: leo-stable-cache
cache_key: leo-fmt-cache
- run:
name: Build and run tests
no_output_timeout: 30m
command: cargo test --all
- persist_to_workspace:
root: ~/
paths: project/
name: Check style
no_output_timeout: 35m
command: cargo fmt --all -- --check
- clear_environment:
cache_key: leo-stable-cache
cache_key: leo-fmt-cache
clippy:
docker:
- image: cimg/rust:1.53
resource_class: xlarge
steps:
- checkout
- setup_environment:
cache_key: leo-clippy-cache
- run:
name: Clippy
no_output_timeout: 35m
command: cargo clippy --all-features --examples --all --benches
- clear_environment:
cache_key: leo-clippy-cache
# code-cov:
# docker:
# - image: cimg/rust:1.53.0
# resource_class: xlarge
# environment:
# RUSTC_BOOTSTRAP: 1
# steps:
# - checkout
# - setup_environment:
# cache_key: leo-codecov-cache
# - run:
# name: Build and run tests
# no_output_timeout: 30m
# command: cargo test --all
# - run:
# name: Install Code Cov Deps
# no_output_timeout: 30m
# command: |
# sudo apt-get update
# sudo apt-get -y install binutils-dev libcurl4-openssl-dev zlib1g-dev libdw-dev libiberty-dev
# - run:
# name: Generate Coverage Report
# no_output_timeout: 30m
# command: |
# wget https://github.com/SimonKagstrom/kcov/archive/master.tar.gz
# tar xzf master.tar.gz
# cd kcov-master
# mkdir build && cd build
# cmake .. && make
# make install DESTDIR=../../kcov-build
# cd ../..
# rm -rf kcov-master
# for file in target/debug/deps/*-*; do if [[ "$file" != *\.* ]]; then mkdir -p "target/cov/$(basename $file)"; ./kcov-build/usr/local/bin/kcov --exclude-pattern=/.cargo,/usr/lib --exclude-region='@kcov_skip(start):@kcov_skip(end)' --verify "target/cov/$(basename $file)" "$file"; fi done
# steps:
# - codecov/upload:
# file: {{}}
# - persist_to_workspace:
# root: ~/
# paths: project/
# - clear_environment:
# cache_key: leo-codecov-cache
leo-executable:
docker:
@ -199,7 +255,8 @@ workflows:
version: 2
main-workflow:
jobs:
- rust-stable
- check-style
- clippy
- leo-executable
- leo-new:
requires:

View File

@ -5,7 +5,7 @@ updates:
schedule:
interval: daily
time: "10:00"
open-pull-requests-limit: 10
open-pull-requests-limit: 20
ignore:
- dependency-name: snarkvm-curves
versions:

View File

@ -1,92 +1,97 @@
name: CI
on:
pull_request:
push:
branches:
- master
- staging
- trying
paths-ignore:
- 'docs/**'
- 'documentation/**'
push:
branches:
- master
- staging
- trying
paths-ignore:
- 'docs/**'
- 'documentation/**'
env:
RUST_BACKTRACE: 1
jobs:
style:
name: Check Style
runs-on: ubuntu-latest
steps:
- name: Checkout
uses: actions/checkout@v1
- name: Install Rust
uses: actions-rs/toolchain@v1
with:
profile: minimal
toolchain: nightly
override: true
components: rustfmt
- name: cargo fmt --check
uses: actions-rs/cargo@v1
with:
command: fmt
args: --all -- --check
clippy:
name: Clippy
runs-on: ubuntu-latest
test-package:
name: Test Package ${{ matrix.os }}
runs-on: ${{ matrix.os }}
strategy:
matrix:
os: [macOS-latest, windows-latest, ubuntu-latest]
include:
- os: ubuntu-latest
sccache-path: /home/runner/.cache/sccache
- os: macos-latest
sccache-path: /Users/runner/Library/Caches/Mozilla.sccache
- os: windows-latest
sccache-path: "C:\\Users\\runneradmin\\AppData\\Local\\Mozilla\\sccache"
env:
RUSTFLAGS: -Dwarnings
RUSTC_WRAPPER: sccache
SCCACHE_CACHE_SIZE: 2G
SCCACHE_DIR: ${{ matrix.sccache-path }}
# SCCACHE_RECACHE: 1 # Uncomment this to clear cache, then comment it back out
steps:
- name: Checkout
uses: actions/checkout@v2
- name: Install Rust
- name: Install sccache Ubuntu
if: matrix.os == 'ubuntu-latest'
env:
LINK: https://github.com/mozilla/sccache/releases/download
SCCACHE_VERSION: v0.2.15
run: |
SCCACHE_FILE=sccache-$SCCACHE_VERSION-x86_64-unknown-linux-musl
mkdir -p $HOME/.local/bin
curl -L "$LINK/$SCCACHE_VERSION/$SCCACHE_FILE.tar.gz" | tar xz
mv -f $SCCACHE_FILE/sccache $HOME/.local/bin/sccache
chmod +x $HOME/.local/bin/sccache
echo "$HOME/.local/bin" >> $GITHUB_PATH
- name: Install sccache Macos
if: matrix.os == 'macos-latest'
run: |
brew update
brew install sccache
- name: Install sccache Windows
if: matrix.os == 'windows-latest'
run: |
iwr -useb get.scoop.sh | iex
Set-ExecutionPolicy RemoteSigned -scope CurrentUser
scoop install sccache
echo "C:\Users\runneradmin\scoop\shims" | Out-File -FilePath $env:GITHUB_PATH -Encoding utf8 -Append
- name: Install Rust Stable
uses: actions-rs/toolchain@v1
with:
profile: minimal
toolchain: stable
override: true
components: clippy
- name: Check examples
uses: actions-rs/cargo@v1
- name: Cache cargo registry
uses: actions/cache@v2
continue-on-error: false
with:
command: clippy
args: --examples --all
path: |
~/.cargo/registry
~/.cargo/git
key: ${{ runner.os }}-cargo-${{ hashFiles('**/Cargo.lock') }}
restore-keys: |
${{ runner.os }}-cargo-
- name: Check examples with all features on stable
uses: actions-rs/cargo@v1
- name: Save sccache
uses: actions/cache@v2
continue-on-error: false
with:
command: clippy
args: --examples --all-features --all
path: ${{ matrix.sccache-path }}
key: ${{ runner.os }}-sccache-${{ hashFiles('**/Cargo.lock') }}
restore-keys: |
${{ runner.os }}-sccache-
- name: Check benchmarks on nightly
uses: actions-rs/cargo@v1
with:
command: clippy
args: --all-features --examples --all --benches
test-package:
name: Test Package
runs-on: ubuntu-latest
strategy:
matrix:
rust:
- stable
- nightly
steps:
- name: Checkout
uses: actions/checkout@v2
- name: Install Rust (${{ matrix.rust }})
uses: actions-rs/toolchain@v1
with:
profile: minimal
toolchain: ${{ matrix.rust }}
override: true
- name: Start sccache server
run: |
sccache --start-server
- name: Install cargo-all-features
run: |
@ -97,21 +102,138 @@ jobs:
cd package
cargo test-all-features
codecov:
name: Code Coverage
runs-on: ubuntu-latest
- name: Print sccache stats
run: sccache --show-stats
- name: Stop sccache server
run: sccache --stop-server || true
test-package-macos_m1:
name: Test Package macOS M1
runs-on: macos-latest
env:
RUSTC_WRAPPER: sccache
SCCACHE_CACHE_SIZE: 2G
SCCACHE_DIR: /Users/runner/Library/Caches/Mozilla.sccache
steps:
- name: Xcode Select
uses: devbotsxyz/xcode-select@v1.1.0
- name: Checkout
uses: actions/checkout@v1
uses: actions/checkout@v2
- name: Install sccache
run: |
brew update
brew install sccache
- name: Install Rust
uses: actions-rs/toolchain@v1
with:
profile: minimal
toolchain: nightly
target: aarch64-apple-darwin
toolchain: stable
override: true
components: rustfmt
- name: Cache cargo registry
uses: actions/cache@v2
continue-on-error: false
with:
path: |
~/.cargo/registry
~/.cargo/git
key: m1-${{ hashFiles('**/Cargo.lock') }}
restore-keys: |
m1-cargo-
- name: Save sccache
uses: actions/cache@v2
continue-on-error: false
with:
path: /Users/runner/Library/Caches/Mozilla.sccache
key: m1-sccache-${{ hashFiles('**/Cargo.lock') }}
restore-keys: |
m1-sccache-
- name: Start sccache server
run: |
sccache --start-server
- name: Install cargo-all-features
run: |
SDKROOT=$(xcrun -sdk macosx11.1 --show-sdk-path) \
MACOSX_DEPLOYMENT_TARGET=$(xcrun -sdk macosx11.1 --show-sdk-platform-version) \
cargo install cargo-all-features
- name: Test
run: |
SDKROOT=$(xcrun -sdk macosx11.1 --show-sdk-path) \
MACOSX_DEPLOYMENT_TARGET=$(xcrun -sdk macosx11.1 --show-sdk-platform-version) \
cd package && cargo test-all-features
- name: Print sccache stats
run: sccache --show-stats
- name: Stop sccache server
run: sccache --stop-server || true
codecov:
name: Code Coverage
runs-on: ubuntu-latest
env:
RUSTC_BOOTSTRAP: 1
RUSTC_WRAPPER: sccache
SCCACHE_CACHE_SIZE: 2G
SCCACHE_DIR: /home/runner/.cache/sccache
steps:
- name: Checkout
uses: actions/checkout@v1
- name: Install sccache Ubuntu
env:
LINK: https://github.com/mozilla/sccache/releases/download
SCCACHE_VERSION: v0.2.15
run: |
SCCACHE_FILE=sccache-$SCCACHE_VERSION-x86_64-unknown-linux-musl
mkdir -p $HOME/.local/bin
curl -L "$LINK/$SCCACHE_VERSION/$SCCACHE_FILE.tar.gz" | tar xz
mv -f $SCCACHE_FILE/sccache $HOME/.local/bin/sccache
chmod +x $HOME/.local/bin/sccache
echo "$HOME/.local/bin" >> $GITHUB_PATH
- name: Install Rust
uses: actions-rs/toolchain@v1
with:
profile: minimal
toolchain: stable
override: true
components: rustfmt
- name: Cache cargo registry
uses: actions/cache@v2
continue-on-error: false
with:
path: |
~/.cargo/registry
~/.cargo/git
key: codecov-${{ hashFiles('**/Cargo.lock') }}
restore-keys: |
codecov-cargo-
- name: Save sccache
uses: actions/cache@v2
continue-on-error: false
with:
path: /Users/runner/Library/Caches/Mozilla.sccache
key: codecov-sccache-${{ hashFiles('**/Cargo.lock') }}
restore-keys: |
codecov-sccache-
- name: Start sccache server
run: |
sccache --start-server
- name: Test
uses: actions-rs/cargo@v1
with:
@ -142,3 +264,9 @@ jobs:
with:
github-token: ${{ secrets.GITHUB_TOKEN }}
token: ${{ secrets.CODECOV_TOKEN }}
- name: Print sccache stats
run: sccache --show-stats
- name: Stop sccache server
run: sccache --stop-server || true

View File

@ -1 +1 @@
v1.5.2
v1.5.3

View File

@ -8,9 +8,9 @@ use_field_init_shorthand = true
use_try_shorthand = true
# Nightly configurations
imports_layout = "HorizontalVertical"
license_template_path = ".resources/license_header"
imports_granularity = "Crate"
overflow_delimited_expr = true
reorder_impl_items = true
version = "Two"
# imports_layout = "HorizontalVertical"
# license_template_path = ".resources/license_header"
# imports_granularity = "Crate"
# overflow_delimited_expr = true
# reorder_impl_items = true
# version = "Two"

105
Cargo.lock generated
View File

@ -76,9 +76,9 @@ dependencies = [
[[package]]
name = "anyhow"
version = "1.0.42"
version = "1.0.43"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "595d3cfa7a60d4555cb5067b99f07142a08ea778de5cf993f7b75c7d8fabc486"
checksum = "28ae2b3dec75a406790005a200b1bd89785afc02517a00ca99ecfe093ee9e6cf"
[[package]]
name = "arrayvec"
@ -88,9 +88,9 @@ checksum = "23b62fc65de8e4e7f52534fb52b0f3ed04746ae267519eef2a83941e8085068b"
[[package]]
name = "assert_cmd"
version = "1.0.7"
version = "2.0.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "3d20831bd004dda4c7c372c19cdabff369f794a95e955b3f13fe460e3e1ae95f"
checksum = "54f002ce7d0c5e809ebb02be78fd503aeed4a511fd0fcaff6e6914cbdabbfa33"
dependencies = [
"bstr",
"doc-comment",
@ -281,7 +281,7 @@ version = "0.2.7"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "4c24dab4283a142afa2fdca129b80ad2c6284e073930f964c3a1293c225ee39a"
dependencies = [
"rustc_version 0.4.0",
"rustc_version",
]
[[package]]
@ -1159,7 +1159,7 @@ checksum = "830d08ce1d1d941e6b30645f1a0eb5643013d835ce3779a5fc208261dbe10f55"
[[package]]
name = "leo-abnf"
version = "1.5.2"
version = "1.5.3"
dependencies = [
"abnf",
"anyhow",
@ -1167,7 +1167,7 @@ dependencies = [
[[package]]
name = "leo-asg"
version = "1.5.2"
version = "1.5.3"
dependencies = [
"criterion",
"indexmap",
@ -1183,14 +1183,14 @@ dependencies = [
[[package]]
name = "leo-asg-passes"
version = "1.5.2"
version = "1.5.3"
dependencies = [
"leo-asg",
]
[[package]]
name = "leo-ast"
version = "1.5.2"
version = "1.5.3"
dependencies = [
"anyhow",
"criterion",
@ -1205,7 +1205,7 @@ dependencies = [
[[package]]
name = "leo-compiler"
version = "1.5.2"
version = "1.5.3"
dependencies = [
"bincode",
"hex",
@ -1243,7 +1243,7 @@ dependencies = [
[[package]]
name = "leo-imports"
version = "1.5.2"
version = "1.5.3"
dependencies = [
"indexmap",
"leo-asg",
@ -1255,7 +1255,7 @@ dependencies = [
[[package]]
name = "leo-input"
version = "1.5.2"
version = "1.5.3"
dependencies = [
"from-pest",
"pest",
@ -1267,7 +1267,7 @@ dependencies = [
[[package]]
name = "leo-lang"
version = "1.5.2"
version = "1.5.3"
dependencies = [
"ansi_term 0.12.1",
"anyhow",
@ -1310,11 +1310,11 @@ dependencies = [
[[package]]
name = "leo-linter"
version = "1.5.2"
version = "1.5.3"
[[package]]
name = "leo-package"
version = "1.5.2"
version = "1.5.3"
dependencies = [
"lazy_static",
"serde",
@ -1327,7 +1327,7 @@ dependencies = [
[[package]]
name = "leo-parser"
version = "1.5.2"
version = "1.5.3"
dependencies = [
"criterion",
"indexmap",
@ -1344,7 +1344,7 @@ dependencies = [
[[package]]
name = "leo-state"
version = "1.5.2"
version = "1.5.3"
dependencies = [
"indexmap",
"leo-ast",
@ -1361,7 +1361,7 @@ dependencies = [
[[package]]
name = "leo-synthesizer"
version = "1.5.2"
version = "1.5.3"
dependencies = [
"hex",
"num-bigint",
@ -1376,7 +1376,7 @@ dependencies = [
[[package]]
name = "leo-test-framework"
version = "1.5.2"
version = "1.5.3"
dependencies = [
"serde",
"serde_json",
@ -2189,15 +2189,6 @@ version = "0.1.20"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "dead70b0b5e03e9c814bcb6b01e03e68f7c57a80aa48c72ec92152ab3e818d49"
[[package]]
name = "rustc_version"
version = "0.3.3"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "f0dfe2087c51c460008730de8b57e6a320782fbfb312e1f4d520e6c6fae155ee"
dependencies = [
"semver 0.11.0",
]
[[package]]
name = "rustc_version"
version = "0.4.0"
@ -2317,9 +2308,9 @@ dependencies = [
[[package]]
name = "serde"
version = "1.0.126"
version = "1.0.127"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "ec7505abeacaec74ae4778d9d9328fe5a5d04253220a85c4ee022239fc996d03"
checksum = "f03b9878abf6d14e6779d3f24f07b2cfa90352cfec4acc5aab8f1ac7f146fae8"
dependencies = [
"serde_derive",
]
@ -2336,9 +2327,9 @@ dependencies = [
[[package]]
name = "serde_derive"
version = "1.0.126"
version = "1.0.127"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "963a7dbc9895aeac7ac90e74f34a5d5261828f79df35cbed41e10189d3804d43"
checksum = "a024926d3432516606328597e0f224a51355a493b49fdd67e9209187cbe55ecc"
dependencies = [
"proc-macro2 1.0.27",
"quote 1.0.9",
@ -2437,9 +2428,9 @@ checksum = "fe0f37c9e8f3c5a4a66ad655a93c74daac4ad00c441533bf5c6e7990bb42604e"
[[package]]
name = "snarkvm-algorithms"
version = "0.7.5"
version = "0.7.9"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "dd8bbefe6252ed85bb073f8ecbc402830e3d119b1aaadcea5a9c9e7a21a99cd2"
checksum = "3534da2cfa71894e4d28c5dcaf9f9c5c94315904c4ace6c86419a8f2ff8b1641"
dependencies = [
"anyhow",
"bitvec",
@ -2465,14 +2456,14 @@ dependencies = [
[[package]]
name = "snarkvm-curves"
version = "0.7.5"
version = "0.7.9"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "62fdf07998a6e88fce7a8139e8282fb6b2702e49624b6d7e10a5cc1c9f014264"
checksum = "83b4de7cd1533c67dd386058b631d7e5ea8b2063ebca212159b13fc1a94ff4a7"
dependencies = [
"derivative",
"rand 0.8.4",
"rand_xorshift",
"rustc_version 0.3.3",
"rustc_version",
"serde",
"snarkvm-fields",
"snarkvm-utilities",
@ -2481,9 +2472,9 @@ dependencies = [
[[package]]
name = "snarkvm-derives"
version = "0.7.5"
version = "0.7.9"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "d42f4d5abda149130149ce3865aef23d380dfcdd97fea7f75fd79b0aee369b29"
checksum = "3e854888634305d8c5c79fe59adaae593971a8b29d3148834f698141b16c2c7b"
dependencies = [
"proc-macro-crate",
"proc-macro-error",
@ -2494,9 +2485,9 @@ dependencies = [
[[package]]
name = "snarkvm-dpc"
version = "0.7.5"
version = "0.7.9"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "af8dd1b815a1101c4014c17cbdffadecb1032e8662fdf5fd4bd67a3c149d8449"
checksum = "c922bb690fbe9c5919f67f2d887452376339a36bf5ffb50dc6b00d58a5650284"
dependencies = [
"anyhow",
"base58",
@ -2526,9 +2517,9 @@ dependencies = [
[[package]]
name = "snarkvm-fields"
version = "0.7.5"
version = "0.7.9"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "2ecd058b3608140610276be1eb1139a032a1bb171969b3ad70550c471d3ae503"
checksum = "bca141a8eae489ea39600b04f0a642059ce076bd3a7d21704b38b90fc87c37f0"
dependencies = [
"anyhow",
"bincode",
@ -2542,9 +2533,9 @@ dependencies = [
[[package]]
name = "snarkvm-gadgets"
version = "0.7.5"
version = "0.7.9"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "7b462bb5e5ac219eafd1a828c73c181e7b23692ade5c49fd72d71bfe4250a6b1"
checksum = "3138cfcaaa27e53cabc7a4fc596b3b0abb47c3cb46fee496e3ac7ce2cd07df9d"
dependencies = [
"derivative",
"digest 0.9.0",
@ -2562,9 +2553,9 @@ dependencies = [
[[package]]
name = "snarkvm-marlin"
version = "0.7.5"
version = "0.7.9"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "2e5b1bb7923a757053c0a544072ec6b298585f83c9f4a3ae777ca048bb6e5589"
checksum = "12e6987cde7b734415afc7afe58a038d224393842ad5dfaba728a601c5c5473d"
dependencies = [
"blake2",
"derivative",
@ -2586,9 +2577,9 @@ dependencies = [
[[package]]
name = "snarkvm-parameters"
version = "0.7.5"
version = "0.7.9"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "14356edda788a3e52ac6e809e6fdbfd5cf7558249bf6051525843b045a73d12a"
checksum = "506cbbbfe27acb4d4e8dd15e49b430dbfb920fd680cfe1c69ab87542083d0422"
dependencies = [
"curl",
"hex",
@ -2599,9 +2590,9 @@ dependencies = [
[[package]]
name = "snarkvm-polycommit"
version = "0.7.5"
version = "0.7.9"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "28fac50de72680316fe57fbbbde2874ae28de7191a3f23ff9e541119951ddaa8"
checksum = "c23a7fa2aab25aa6fc3b7fb27b3d639936725a5c29b29936d1530b64bd011e67"
dependencies = [
"derivative",
"digest 0.9.0",
@ -2618,15 +2609,15 @@ dependencies = [
[[package]]
name = "snarkvm-profiler"
version = "0.7.5"
version = "0.7.9"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "2ebfa546f0376a1348b857a9defdb3f4505a0420d82f8caa2b0cebbe197245fa"
checksum = "f7d80cc343b9e19e0f38582fa7e17e6263c4c7449122cf9a606279567ff33d71"
[[package]]
name = "snarkvm-r1cs"
version = "0.7.5"
version = "0.7.9"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "2aca9bb7105244ebc91f964b11a1ae63f173a77181307d1fa94f04e15dbde137"
checksum = "537f2123c7da8a9d3482523156318479790c41e390d33f6936b89a3ed9eee0a8"
dependencies = [
"cfg-if 1.0.0",
"fxhash",
@ -2639,9 +2630,9 @@ dependencies = [
[[package]]
name = "snarkvm-utilities"
version = "0.7.5"
version = "0.7.9"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "15b7ecf6a7afdd60a45cbd5ffab75185c296d8a4bf5eb20f3912384b1d4027c2"
checksum = "a6d1565a7c2a320b711308188adf84980013872e579ae2e6abffe8796eb8e6fe"
dependencies = [
"anyhow",
"bincode",

View File

@ -1,6 +1,6 @@
[package]
name = "leo-lang"
version = "1.5.2"
version = "1.5.3"
authors = [ "The Aleo Team <hello@aleo.org>" ]
description = "The Leo programming language"
homepage = "https://aleo.org"
@ -43,53 +43,53 @@ members = [
[dependencies.leo-ast]
path = "./ast"
version = "1.5.2"
version = "1.5.3"
[dependencies.leo-compiler]
path = "./compiler"
version = "1.5.2"
version = "1.5.3"
[dependencies.leo-imports]
path = "./imports"
version = "1.5.2"
version = "1.5.3"
[dependencies.leo-input]
path = "./input"
version = "1.5.2"
version = "1.5.3"
[dependencies.leo-package]
path = "./package"
version = "1.5.2"
version = "1.5.3"
[dependencies.leo-parser]
path = "./parser"
version = "1.5.2"
version = "1.5.3"
[dependencies.leo-state]
path = "./state"
version = "1.5.2"
version = "1.5.3"
[dependencies.leo-synthesizer]
path = "./synthesizer"
version = "1.5.2"
version = "1.5.3"
[dependencies.snarkvm-algorithms]
version = "0.7.4"
version = "0.7.6"
[dependencies.snarkvm-curves]
version = "0.7.5"
version = "0.7.9"
default-features = false
[dependencies.snarkvm-gadgets]
version = "0.7.5"
version = "0.7.8"
default-features = false
[dependencies.snarkvm-r1cs]
version = "0.7.5"
version = "0.7.8"
default-features = false
[dependencies.snarkvm-utilities]
version = "0.7.4"
version = "0.7.6"
[dependencies.anyhow]
version = "1.0"
@ -162,7 +162,7 @@ version = "0.12.1"
version = "0.11.2"
[dev-dependencies.assert_cmd]
version = "1.0.7"
version = "2.0.0"
[dev-dependencies.test_dir]
version = "0.1.0"

View File

@ -1,6 +1,6 @@
[package]
name = "leo-asg-passes"
version = "1.5.2"
version = "1.5.3"
authors = [ "The Aleo Team <hello@aleo.org>" ]
description = "The Leo programming language"
homepage = "https://aleo.org"
@ -22,4 +22,4 @@ path = "src/lib.rs"
[dependencies.leo-asg]
path = "../asg"
version = "1.5.2"
version = "1.5.3"

View File

@ -1,6 +1,6 @@
[package]
name = "leo-asg"
version = "1.5.2"
version = "1.5.3"
authors = [ "The Aleo Team <hello@aleo.org>" ]
description = "ASG of the Leo programming language"
homepage = "https://aleo.org"
@ -30,7 +30,7 @@ version = "1.7"
version = "1.0"
[dependencies.leo-ast]
version = "1.5.2"
version = "1.5.3"
path = "../ast"
[dependencies.num-bigint]

View File

@ -15,14 +15,7 @@
// along with the Leo library. If not, see <https://www.gnu.org/licenses/>.
use crate::{
statement::*,
BoolAnd,
Expression,
Monoid,
MonoidalReducerExpression,
MonoidalReducerStatement,
Node,
Span,
statement::*, BoolAnd, Expression, Monoid, MonoidalReducerExpression, MonoidalReducerStatement, Node, Span,
};
pub struct ReturnPathReducer {

View File

@ -315,16 +315,16 @@ impl ConstInt {
pub fn parse(int_type: &IntegerType, value: &str, span: &Span) -> Result<ConstInt, AsgConvertError> {
Ok(match int_type {
IntegerType::I8 => ConstInt::I8(value.parse().map_err(|_| AsgConvertError::invalid_int(&value, span))?),
IntegerType::I16 => ConstInt::I16(value.parse().map_err(|_| AsgConvertError::invalid_int(&value, span))?),
IntegerType::I32 => ConstInt::I32(value.parse().map_err(|_| AsgConvertError::invalid_int(&value, span))?),
IntegerType::I64 => ConstInt::I64(value.parse().map_err(|_| AsgConvertError::invalid_int(&value, span))?),
IntegerType::I128 => ConstInt::I128(value.parse().map_err(|_| AsgConvertError::invalid_int(&value, span))?),
IntegerType::U8 => ConstInt::U8(value.parse().map_err(|_| AsgConvertError::invalid_int(&value, span))?),
IntegerType::U16 => ConstInt::U16(value.parse().map_err(|_| AsgConvertError::invalid_int(&value, span))?),
IntegerType::U32 => ConstInt::U32(value.parse().map_err(|_| AsgConvertError::invalid_int(&value, span))?),
IntegerType::U64 => ConstInt::U64(value.parse().map_err(|_| AsgConvertError::invalid_int(&value, span))?),
IntegerType::U128 => ConstInt::U128(value.parse().map_err(|_| AsgConvertError::invalid_int(&value, span))?),
IntegerType::I8 => ConstInt::I8(value.parse().map_err(|_| AsgConvertError::invalid_int(value, span))?),
IntegerType::I16 => ConstInt::I16(value.parse().map_err(|_| AsgConvertError::invalid_int(value, span))?),
IntegerType::I32 => ConstInt::I32(value.parse().map_err(|_| AsgConvertError::invalid_int(value, span))?),
IntegerType::I64 => ConstInt::I64(value.parse().map_err(|_| AsgConvertError::invalid_int(value, span))?),
IntegerType::I128 => ConstInt::I128(value.parse().map_err(|_| AsgConvertError::invalid_int(value, span))?),
IntegerType::U8 => ConstInt::U8(value.parse().map_err(|_| AsgConvertError::invalid_int(value, span))?),
IntegerType::U16 => ConstInt::U16(value.parse().map_err(|_| AsgConvertError::invalid_int(value, span))?),
IntegerType::U32 => ConstInt::U32(value.parse().map_err(|_| AsgConvertError::invalid_int(value, span))?),
IntegerType::U64 => ConstInt::U64(value.parse().map_err(|_| AsgConvertError::invalid_int(value, span))?),
IntegerType::U128 => ConstInt::U128(value.parse().map_err(|_| AsgConvertError::invalid_int(value, span))?),
})
}
}

View File

@ -15,19 +15,8 @@
// along with the Leo library. If not, see <https://www.gnu.org/licenses/>.
use crate::{
AsgConvertError,
CircuitMember,
ConstValue,
Expression,
ExpressionNode,
FromAst,
Function,
FunctionQualifier,
Node,
PartialType,
Scope,
Span,
Type,
AsgConvertError, CircuitMember, ConstValue, Expression, ExpressionNode, FromAst, Function, FunctionQualifier, Node,
PartialType, Scope, Span, Type,
};
pub use leo_ast::{BinaryOperation, Node as AstNode};

View File

@ -15,19 +15,8 @@
// along with the Leo library. If not, see <https://www.gnu.org/licenses/>.
use crate::{
AsgConvertError,
Circuit,
CircuitMember,
ConstValue,
Expression,
ExpressionNode,
FromAst,
Identifier,
Node,
PartialType,
Scope,
Span,
Type,
AsgConvertError, Circuit, CircuitMember, ConstValue, Expression, ExpressionNode, FromAst, Identifier, Node,
PartialType, Scope, Span, Type,
};
use std::cell::Cell;

View File

@ -15,19 +15,8 @@
// along with the Leo library. If not, see <https://www.gnu.org/licenses/>.
use crate::{
AsgConvertError,
Circuit,
CircuitMember,
ConstValue,
Expression,
ExpressionNode,
FromAst,
Identifier,
Node,
PartialType,
Scope,
Span,
Type,
AsgConvertError, Circuit, CircuitMember, ConstValue, Expression, ExpressionNode, FromAst, Identifier, Node,
PartialType, Scope, Span, Type,
};
use indexmap::{IndexMap, IndexSet};

View File

@ -15,19 +15,8 @@
// along with the Leo library. If not, see <https://www.gnu.org/licenses/>.
use crate::{
AsgConvertError,
CharValue,
ConstInt,
ConstValue,
Expression,
ExpressionNode,
FromAst,
GroupValue,
Node,
PartialType,
Scope,
Span,
Type,
AsgConvertError, CharValue, ConstInt, ConstValue, Expression, ExpressionNode, FromAst, GroupValue, Node,
PartialType, Scope, Span, Type,
};
use std::cell::Cell;
@ -115,7 +104,7 @@ impl<'a> FromAst<'a, leo_ast::ValueExpression> for Constant<'a> {
value: ConstValue::Boolean(
value
.parse::<bool>()
.map_err(|_| AsgConvertError::invalid_boolean(&value, span))?,
.map_err(|_| AsgConvertError::invalid_boolean(value, span))?,
),
}
}
@ -151,7 +140,7 @@ impl<'a> FromAst<'a, leo_ast::ValueExpression> for Constant<'a> {
Constant {
parent: Cell::new(None),
span: Some(span.clone()),
value: ConstValue::Field(value.parse().map_err(|_| AsgConvertError::invalid_int(&value, span))?),
value: ConstValue::Field(value.parse().map_err(|_| AsgConvertError::invalid_int(value, span))?),
}
}
Group(value) => {
@ -188,7 +177,7 @@ impl<'a> FromAst<'a, leo_ast::ValueExpression> for Constant<'a> {
Some(PartialType::Type(Type::Field)) => Constant {
parent: Cell::new(None),
span: Some(span.clone()),
value: ConstValue::Field(value.parse().map_err(|_| AsgConvertError::invalid_int(&value, span))?),
value: ConstValue::Field(value.parse().map_err(|_| AsgConvertError::invalid_int(value, span))?),
},
Some(PartialType::Type(Type::Group)) => Constant {
parent: Cell::new(None),

View File

@ -341,7 +341,7 @@ impl<'a> FromAst<'a, leo_ast::Expression> for &'a Expression<'a> {
.context
.alloc_expression(CallExpression::from_ast(scope, call, expected_type).map(Expression::Call)?),
};
expression.enforce_parents(&expression);
expression.enforce_parents(expression);
Ok(expression)
}
}

View File

@ -15,20 +15,8 @@
// along with the Leo library. If not, see <https://www.gnu.org/licenses/>.
use crate::{
AsgConvertError,
ConstValue,
Constant,
DefinitionStatement,
Expression,
ExpressionNode,
FromAst,
Node,
PartialType,
Scope,
Span,
Statement,
Type,
Variable,
AsgConvertError, ConstValue, Constant, DefinitionStatement, Expression, ExpressionNode, FromAst, Node, PartialType,
Scope, Span, Statement, Type, Variable,
};
use std::cell::Cell;

View File

@ -15,16 +15,7 @@
// along with the Leo library. If not, see <https://www.gnu.org/licenses/>.
use crate::{
AsgContextInner,
AsgConvertError,
Circuit,
Expression,
Function,
PartialType,
Scope,
Span,
Statement,
Variable,
AsgContextInner, AsgConvertError, Circuit, Expression, Function, PartialType, Scope, Span, Statement, Variable,
};
/// A node in the abstract semantic graph.

View File

@ -15,18 +15,8 @@
// along with the Leo library. If not, see <https://www.gnu.org/licenses/>.
use crate::{
AsgConvertError,
BlockStatement,
Circuit,
FromAst,
Identifier,
MonoidalDirector,
ReturnPathReducer,
Scope,
Span,
Statement,
Type,
Variable,
AsgConvertError, BlockStatement, Circuit, FromAst, Identifier, MonoidalDirector, ReturnPathReducer, Scope, Span,
Statement, Type, Variable,
};
use indexmap::IndexMap;
pub use leo_ast::Annotation;
@ -101,7 +91,7 @@ impl<'a> Function<'a> {
let variable = scope.context.alloc_variable(RefCell::new(crate::InnerVariable {
id: scope.context.get_id(),
name: identifier.clone(),
type_: scope.resolve_ast_type(&type_)?,
type_: scope.resolve_ast_type(type_)?,
mutable: *mutable,
const_: *const_,
declaration: crate::VariableDeclaration::Parameter,

View File

@ -25,15 +25,7 @@ mod function;
pub use function::*;
use crate::{
node::FromAst,
ArenaNode,
AsgContext,
AsgConvertError,
DefinitionStatement,
ImportResolver,
Input,
Scope,
Statement,
node::FromAst, ArenaNode, AsgContext, AsgConvertError, DefinitionStatement, ImportResolver, Input, Scope, Statement,
};
use leo_ast::{PackageAccess, PackageOrPackages, Span};

View File

@ -308,6 +308,6 @@ impl<'a, T: Monoid, R: MonoidalReducerProgram<'a, T>> MonoidalDirector<'a, T, R>
let circuits = input.circuits.iter().map(|(_, c)| self.reduce_circuit(c)).collect();
self.reducer
.reduce_program(&input, imported_modules, functions, circuits)
.reduce_program(input, imported_modules, functions, circuits)
}
}

View File

@ -15,22 +15,8 @@
// along with the Leo library. If not, see <https://www.gnu.org/licenses/>.
use crate::{
AsgConvertError,
CircuitMember,
ConstInt,
ConstValue,
Expression,
ExpressionNode,
FromAst,
Identifier,
IntegerType,
Node,
PartialType,
Scope,
Span,
Statement,
Type,
Variable,
AsgConvertError, CircuitMember, ConstInt, ConstValue, Expression, ExpressionNode, FromAst, Identifier, IntegerType,
Node, PartialType, Scope, Span, Statement, Type, Variable,
};
pub use leo_ast::AssignOperation;
use leo_ast::AssigneeAccess as AstAssigneeAccess;
@ -79,12 +65,12 @@ impl<'a> FromAst<'a, leo_ast::AssignStatement> for &'a Statement<'a> {
}
} else {
scope
.resolve_variable(&name)
.ok_or_else(|| AsgConvertError::unresolved_reference(name, &span))?
.resolve_variable(name)
.ok_or_else(|| AsgConvertError::unresolved_reference(name, span))?
};
if !variable.borrow().mutable {
return Err(AsgConvertError::immutable_assignment(&name, &statement.span));
return Err(AsgConvertError::immutable_assignment(name, &statement.span));
}
let mut target_type: Option<PartialType> = Some(variable.borrow().type_.clone().into());
@ -123,13 +109,13 @@ impl<'a> FromAst<'a, leo_ast::AssignStatement> for &'a Statement<'a> {
) {
let left = match left {
ConstValue::Int(x) => x.to_usize().ok_or_else(|| {
AsgConvertError::invalid_assign_index(&name, &x.to_string(), &statement.span)
AsgConvertError::invalid_assign_index(name, &x.to_string(), &statement.span)
})?,
_ => unimplemented!(),
};
let right = match right {
ConstValue::Int(x) => x.to_usize().ok_or_else(|| {
AsgConvertError::invalid_assign_index(&name, &x.to_string(), &statement.span)
AsgConvertError::invalid_assign_index(name, &x.to_string(), &statement.span)
})?,
_ => unimplemented!(),
};
@ -137,7 +123,7 @@ impl<'a> FromAst<'a, leo_ast::AssignStatement> for &'a Statement<'a> {
target_type = Some(PartialType::Array(item.clone(), Some((right - left) as usize)))
} else {
return Err(AsgConvertError::invalid_backwards_assignment(
&name,
name,
left,
right,
&statement.span,
@ -145,7 +131,7 @@ impl<'a> FromAst<'a, leo_ast::AssignStatement> for &'a Statement<'a> {
}
}
}
_ => return Err(AsgConvertError::index_into_non_array(&name, &statement.span)),
_ => return Err(AsgConvertError::index_into_non_array(name, &statement.span)),
}
AssignAccess::ArrayRange(Cell::new(left), Cell::new(right))
@ -153,7 +139,7 @@ impl<'a> FromAst<'a, leo_ast::AssignStatement> for &'a Statement<'a> {
AstAssigneeAccess::ArrayIndex(index) => {
target_type = match target_type.clone() {
Some(PartialType::Array(item, _)) => item.map(|x| *x),
_ => return Err(AsgConvertError::index_into_non_array(&name, &statement.span)),
_ => return Err(AsgConvertError::index_into_non_array(name, &statement.span)),
};
AssignAccess::ArrayIndex(Cell::new(<&Expression<'a>>::from_ast(
scope,
@ -171,7 +157,7 @@ impl<'a> FromAst<'a, leo_ast::AssignStatement> for &'a Statement<'a> {
.get(index)
.cloned()
.ok_or_else(|| AsgConvertError::tuple_index_out_of_bounds(index, &statement.span))?,
_ => return Err(AsgConvertError::index_into_non_tuple(&name, &statement.span)),
_ => return Err(AsgConvertError::index_into_non_tuple(name, &statement.span)),
};
AssignAccess::Tuple(index)
}

View File

@ -42,7 +42,7 @@ impl<'a> FromAst<'a, leo_ast::Block> for BlockStatement<'a> {
let mut output = vec![];
for item in statement.statements.iter() {
output.push(Cell::new(<&'a Statement<'a>>::from_ast(&new_scope, item, None)?));
output.push(Cell::new(<&'a Statement<'a>>::from_ast(new_scope, item, None)?));
}
Ok(BlockStatement {
parent: Cell::new(None),

View File

@ -15,18 +15,8 @@
// along with the Leo library. If not, see <https://www.gnu.org/licenses/>.
use crate::{
AsgConvertError,
Expression,
ExpressionNode,
FromAst,
InnerVariable,
Node,
PartialType,
Scope,
Span,
Statement,
Type,
Variable,
AsgConvertError, Expression, ExpressionNode, FromAst, InnerVariable, Node, PartialType, Scope, Span, Statement,
Type, Variable,
};
use std::cell::{Cell, RefCell};
@ -44,12 +34,15 @@ impl<'a> DefinitionStatement<'a> {
self.variables
.iter()
.map(|variable| {
(variable.borrow().name.name.to_string(), DefinitionStatement {
parent: self.parent.clone(),
span: self.span.clone(),
variables: vec![variable],
value: self.value.clone(),
})
(
variable.borrow().name.name.to_string(),
DefinitionStatement {
parent: self.parent.clone(),
span: self.span.clone(),
variables: vec![variable],
value: self.value.clone(),
},
)
})
.collect()
}
@ -70,7 +63,7 @@ impl<'a> FromAst<'a, leo_ast::DefinitionStatement> for &'a Statement<'a> {
let type_ = statement
.type_
.as_ref()
.map(|x| scope.resolve_ast_type(&x))
.map(|x| scope.resolve_ast_type(x))
.transpose()?;
let value = <&Expression<'a>>::from_ast(scope, &statement.value, type_.clone().map(Into::into))?;

View File

@ -17,16 +17,7 @@
use leo_ast::IntegerType;
use crate::{
AsgConvertError,
Expression,
ExpressionNode,
FromAst,
InnerVariable,
Node,
PartialType,
Scope,
Span,
Statement,
AsgConvertError, Expression, ExpressionNode, FromAst, InnerVariable, Node, PartialType, Scope, Span, Statement,
Variable,
};

View File

@ -1,6 +1,6 @@
[package]
name = "leo-ast"
version = "1.5.2"
version = "1.5.3"
authors = [ "The Aleo Team <hello@aleo.org>" ]
description = "Core AST of the Leo programming language"
homepage = "https://aleo.org"
@ -19,7 +19,7 @@ edition = "2018"
[dependencies.leo-input]
path = "../input"
version = "1.5.2"
version = "1.5.3"
[dependencies.leo-parser]
path = "../parser"

View File

@ -21,13 +21,9 @@ use tendril::StrTendril;
use crate::Node;
use serde::{
de::{
Visitor,
{self},
Visitor, {self},
},
Deserialize,
Deserializer,
Serialize,
Serializer,
Deserialize, Deserializer, Serialize, Serializer,
};
use std::{
collections::BTreeMap,

View File

@ -15,13 +15,7 @@
// along with the Leo library. If not, see <https://www.gnu.org/licenses/>.
use crate::{
ArrayDimensions,
CircuitImpliedVariableDefinition,
GroupValue,
Identifier,
IntegerType,
PositiveNumber,
Span,
ArrayDimensions, CircuitImpliedVariableDefinition, GroupValue, Identifier, IntegerType, PositiveNumber, Span,
SpreadOrExpression,
};

View File

@ -16,11 +16,8 @@
use crate::common::span::Span;
use leo_input::values::{
GroupCoordinate as InputGroupCoordinate,
Inferred as InputInferred,
NumberValue as InputNumberValue,
SignHigh as InputSignHigh,
SignLow as InputSignLow,
GroupCoordinate as InputGroupCoordinate, Inferred as InputInferred, NumberValue as InputNumberValue,
SignHigh as InputSignHigh, SignLow as InputSignLow,
};
use serde::{Deserialize, Serialize};

View File

@ -16,9 +16,7 @@
use crate::{common::span::Span, groups::GroupCoordinate};
use leo_input::values::{
GroupRepresentation as InputGroupRepresentation,
GroupTuple as InputGroupTuple,
GroupValue as InputGroupValue,
GroupRepresentation as InputGroupRepresentation, GroupTuple as InputGroupTuple, GroupValue as InputGroupValue,
};
use serde::{Deserialize, Serialize};

View File

@ -20,15 +20,8 @@ use leo_input::{
expressions::{ArrayInitializerExpression, ArrayInlineExpression, Expression, StringExpression, TupleExpression},
types::{ArrayType, CharType, DataType, IntegerType, TupleType, Type},
values::{
Address,
AddressValue,
BooleanValue,
CharValue as InputCharValue,
FieldValue,
GroupValue as InputGroupValue,
IntegerValue,
NumberValue,
Value,
Address, AddressValue, BooleanValue, CharValue as InputCharValue, FieldValue, GroupValue as InputGroupValue,
IntegerValue, NumberValue, Value,
},
};
use pest::Span;

View File

@ -40,7 +40,11 @@ impl PublicState {
}
pub fn len(&self) -> usize {
if self.state.is_present() { 1usize } else { 0usize }
if self.state.is_present() {
1usize
} else {
0usize
}
}
/// Parse all input variables included in a file and store them in `self`.

View File

@ -47,7 +47,7 @@ impl Canonicalizer {
let mut left = Box::new(start);
for access in accesses.iter() {
match self.canonicalize_assignee_access(&access) {
match self.canonicalize_assignee_access(access) {
AssigneeAccess::ArrayIndex(index) => {
left = Box::new(Expression::ArrayAccess(ArrayAccessExpression {
array: left,
@ -276,6 +276,11 @@ impl Canonicalizer {
span: call.span.clone(),
});
}
Expression::Identifier(identifier) => {
if identifier.name.as_ref() == "Self" && self.circuit_name.is_some() {
return Expression::Identifier(self.circuit_name.as_ref().unwrap().clone());
}
}
_ => {}
}
@ -290,7 +295,7 @@ impl Canonicalizer {
AssigneeAccess::ArrayRange(left, right)
}
AssigneeAccess::ArrayIndex(index) => AssigneeAccess::ArrayIndex(self.canonicalize_expression(&index)),
AssigneeAccess::ArrayIndex(index) => AssigneeAccess::ArrayIndex(self.canonicalize_expression(index)),
_ => access.clone(),
}
}
@ -313,7 +318,7 @@ impl Canonicalizer {
let statements = block
.statements
.iter()
.map(|block_statement| self.canonicalize_statement(&block_statement))
.map(|block_statement| self.canonicalize_statement(block_statement))
.collect();
Block {

View File

@ -50,34 +50,32 @@ impl<R: ReconstructingReducer> ReconstructingDirector<R> {
// Expressions
pub fn reduce_expression(&mut self, expression: &Expression) -> Result<Expression, ReducerError> {
let new = match expression {
Expression::Identifier(identifier) => Expression::Identifier(self.reduce_identifier(&identifier)?),
Expression::Value(value) => self.reduce_value(&value)?,
Expression::Binary(binary) => Expression::Binary(self.reduce_binary(&binary)?),
Expression::Unary(unary) => Expression::Unary(self.reduce_unary(&unary)?),
Expression::Ternary(ternary) => Expression::Ternary(self.reduce_ternary(&ternary)?),
Expression::Cast(cast) => Expression::Cast(self.reduce_cast(&cast)?),
Expression::Identifier(identifier) => Expression::Identifier(self.reduce_identifier(identifier)?),
Expression::Value(value) => self.reduce_value(value)?,
Expression::Binary(binary) => Expression::Binary(self.reduce_binary(binary)?),
Expression::Unary(unary) => Expression::Unary(self.reduce_unary(unary)?),
Expression::Ternary(ternary) => Expression::Ternary(self.reduce_ternary(ternary)?),
Expression::Cast(cast) => Expression::Cast(self.reduce_cast(cast)?),
Expression::ArrayInline(array_inline) => Expression::ArrayInline(self.reduce_array_inline(&array_inline)?),
Expression::ArrayInit(array_init) => Expression::ArrayInit(self.reduce_array_init(&array_init)?),
Expression::ArrayAccess(array_access) => Expression::ArrayAccess(self.reduce_array_access(&array_access)?),
Expression::ArrayInline(array_inline) => Expression::ArrayInline(self.reduce_array_inline(array_inline)?),
Expression::ArrayInit(array_init) => Expression::ArrayInit(self.reduce_array_init(array_init)?),
Expression::ArrayAccess(array_access) => Expression::ArrayAccess(self.reduce_array_access(array_access)?),
Expression::ArrayRangeAccess(array_range_access) => {
Expression::ArrayRangeAccess(self.reduce_array_range_access(&array_range_access)?)
Expression::ArrayRangeAccess(self.reduce_array_range_access(array_range_access)?)
}
Expression::TupleInit(tuple_init) => Expression::TupleInit(self.reduce_tuple_init(&tuple_init)?),
Expression::TupleAccess(tuple_access) => Expression::TupleAccess(self.reduce_tuple_access(&tuple_access)?),
Expression::TupleInit(tuple_init) => Expression::TupleInit(self.reduce_tuple_init(tuple_init)?),
Expression::TupleAccess(tuple_access) => Expression::TupleAccess(self.reduce_tuple_access(tuple_access)?),
Expression::CircuitInit(circuit_init) => Expression::CircuitInit(self.reduce_circuit_init(&circuit_init)?),
Expression::CircuitInit(circuit_init) => Expression::CircuitInit(self.reduce_circuit_init(circuit_init)?),
Expression::CircuitMemberAccess(circuit_member_access) => {
Expression::CircuitMemberAccess(self.reduce_circuit_member_access(&circuit_member_access)?)
Expression::CircuitMemberAccess(self.reduce_circuit_member_access(circuit_member_access)?)
}
Expression::CircuitStaticFunctionAccess(circuit_static_fn_access) => {
Expression::CircuitStaticFunctionAccess(
self.reduce_circuit_static_fn_access(&circuit_static_fn_access)?,
)
Expression::CircuitStaticFunctionAccess(self.reduce_circuit_static_fn_access(circuit_static_fn_access)?)
}
Expression::Call(call) => Expression::Call(self.reduce_call(&call)?),
Expression::Call(call) => Expression::Call(self.reduce_call(call)?),
};
self.reducer.reduce_expression(expression, new)
@ -93,7 +91,7 @@ impl<R: ReconstructingReducer> ReconstructingDirector<R> {
pub fn reduce_group_value(&mut self, group_value: &GroupValue) -> Result<GroupValue, ReducerError> {
let new = match group_value {
GroupValue::Tuple(group_tuple) => GroupValue::Tuple(self.reduce_group_tuple(&group_tuple)?),
GroupValue::Tuple(group_tuple) => GroupValue::Tuple(self.reduce_group_tuple(group_tuple)?),
_ => group_value.clone(),
};
@ -107,9 +105,9 @@ impl<R: ReconstructingReducer> ReconstructingDirector<R> {
pub fn reduce_value(&mut self, value: &ValueExpression) -> Result<Expression, ReducerError> {
let new = match value {
ValueExpression::Group(group_value) => {
Expression::Value(ValueExpression::Group(Box::new(self.reduce_group_value(&group_value)?)))
Expression::Value(ValueExpression::Group(Box::new(self.reduce_group_value(group_value)?)))
}
ValueExpression::String(string, span) => self.reduce_string(string, &span)?,
ValueExpression::String(string, span) => self.reduce_string(string, span)?,
_ => Expression::Value(value.clone()),
};
@ -284,14 +282,14 @@ impl<R: ReconstructingReducer> ReconstructingDirector<R> {
// Statements
pub fn reduce_statement(&mut self, statement: &Statement) -> Result<Statement, ReducerError> {
let new = match statement {
Statement::Return(return_statement) => Statement::Return(self.reduce_return(&return_statement)?),
Statement::Definition(definition) => Statement::Definition(self.reduce_definition(&definition)?),
Statement::Assign(assign) => Statement::Assign(self.reduce_assign(&assign)?),
Statement::Conditional(conditional) => Statement::Conditional(self.reduce_conditional(&conditional)?),
Statement::Iteration(iteration) => Statement::Iteration(self.reduce_iteration(&iteration)?),
Statement::Console(console) => Statement::Console(self.reduce_console(&console)?),
Statement::Expression(expression) => Statement::Expression(self.reduce_expression_statement(&expression)?),
Statement::Block(block) => Statement::Block(self.reduce_block(&block)?),
Statement::Return(return_statement) => Statement::Return(self.reduce_return(return_statement)?),
Statement::Definition(definition) => Statement::Definition(self.reduce_definition(definition)?),
Statement::Assign(assign) => Statement::Assign(self.reduce_assign(assign)?),
Statement::Conditional(conditional) => Statement::Conditional(self.reduce_conditional(conditional)?),
Statement::Iteration(iteration) => Statement::Iteration(self.reduce_iteration(iteration)?),
Statement::Console(console) => Statement::Console(self.reduce_console(console)?),
Statement::Expression(expression) => Statement::Expression(self.reduce_expression_statement(expression)?),
Statement::Block(block) => Statement::Block(self.reduce_block(block)?),
};
self.reducer.reduce_statement(statement, new)
@ -334,8 +332,8 @@ impl<R: ReconstructingReducer> ReconstructingDirector<R> {
AssigneeAccess::ArrayRange(left, right)
}
AssigneeAccess::ArrayIndex(index) => AssigneeAccess::ArrayIndex(self.reduce_expression(&index)?),
AssigneeAccess::Member(identifier) => AssigneeAccess::Member(self.reduce_identifier(&identifier)?),
AssigneeAccess::ArrayIndex(index) => AssigneeAccess::ArrayIndex(self.reduce_expression(index)?),
AssigneeAccess::Member(identifier) => AssigneeAccess::Member(self.reduce_identifier(identifier)?),
_ => access.clone(),
};
@ -462,7 +460,7 @@ impl<R: ReconstructingReducer> ReconstructingDirector<R> {
let mut global_consts = IndexMap::new();
for (name, definition) in program.global_consts.iter() {
global_consts.insert(name.clone(), self.reduce_definition(&definition)?);
global_consts.insert(name.clone(), self.reduce_definition(definition)?);
}
self.reducer.reduce_program(
@ -532,12 +530,10 @@ impl<R: ReconstructingReducer> ReconstructingDirector<R> {
pub fn reduce_circuit_member(&mut self, circuit_member: &CircuitMember) -> Result<CircuitMember, ReducerError> {
let new = match circuit_member {
CircuitMember::CircuitVariable(identifier, type_) => CircuitMember::CircuitVariable(
self.reduce_identifier(&identifier)?,
self.reduce_type(&type_, &identifier.span)?,
self.reduce_identifier(identifier)?,
self.reduce_type(type_, &identifier.span)?,
),
CircuitMember::CircuitFunction(function) => {
CircuitMember::CircuitFunction(self.reduce_function(&function)?)
}
CircuitMember::CircuitFunction(function) => CircuitMember::CircuitFunction(self.reduce_function(function)?),
};
self.reducer.reduce_circuit_member(circuit_member, new)

View File

@ -15,8 +15,7 @@
// along with the Leo library. If not, see <https://www.gnu.org/licenses/>.
use leo_input::types::{
IntegerType as InputIntegerType,
SignedIntegerType as InputSignedIntegerType,
IntegerType as InputIntegerType, SignedIntegerType as InputSignedIntegerType,
UnsignedIntegerType as InputUnsignedIntegerType,
};

View File

@ -16,10 +16,7 @@
use crate::{ArrayDimensions, Identifier, IntegerType};
use leo_input::types::{
ArrayType as InputArrayType,
DataType as InputDataType,
TupleType as InputTupleType,
Type as InputType,
ArrayType as InputArrayType, DataType as InputDataType, TupleType as InputTupleType, Type as InputType,
};
use serde::{Deserialize, Serialize};
@ -70,8 +67,8 @@ impl Type {
(Type::Char, Type::Char) => true,
(Type::Field, Type::Field) => true,
(Type::Group, Type::Group) => true,
(Type::IntegerType(left), Type::IntegerType(right)) => left.eq(&right),
(Type::Circuit(left), Type::Circuit(right)) => left.eq(&right),
(Type::IntegerType(left), Type::IntegerType(right)) => left.eq(right),
(Type::Circuit(left), Type::Circuit(right)) => left.eq(right),
(Type::SelfType, Type::SelfType) => true,
(Type::Array(left_type, left_dim), Type::Array(right_type, right_dim)) => {
// Convert array dimensions to owned.

View File

@ -1,6 +1,6 @@
[package]
name = "leo-compiler"
version = "1.5.2"
version = "1.5.3"
authors = [ "The Aleo Team <hello@aleo.org>" ]
description = "Compiler of the Leo programming language"
homepage = "https://aleo.org"
@ -19,66 +19,66 @@ edition = "2018"
[dependencies.leo-ast]
path = "../ast"
version = "1.5.2"
version = "1.5.3"
[dependencies.leo-imports]
path = "../imports"
version = "1.5.2"
version = "1.5.3"
[dependencies.leo-input]
path = "../input"
version = "1.5.2"
version = "1.5.3"
[dependencies.leo-package]
path = "../package"
version = "1.5.2"
version = "1.5.3"
[dependencies.leo-state]
path = "../state"
version = "1.5.2"
version = "1.5.3"
[dependencies.leo-asg]
path = "../asg"
version = "1.5.2"
version = "1.5.3"
[dependencies.leo-parser]
path = "../parser"
version = "1.5.2"
version = "1.5.3"
[dependencies.leo-asg-passes]
path = "../asg-passes"
version = "1.5.2"
version = "1.5.3"
[dependencies.leo-synthesizer]
path = "../synthesizer"
version = "1.5.2"
version = "1.5.3"
[dependencies.tendril]
version = "0.4"
[dependencies.snarkvm-curves]
version = "0.7.5"
version = "0.7.9"
default-features = false
[dependencies.snarkvm-fields]
version = "0.7.5"
version = "0.7.7"
default-features = false
[dependencies.snarkvm-dpc]
version = "0.7.5"
version = "0.7.9"
default-features = false
[dependencies.snarkvm-gadgets]
version = "0.7.5"
version = "0.7.8"
default-features = false
features = ["curves"]
features = [ "curves" ]
[dependencies.snarkvm-r1cs]
version = "0.7.5"
version = "0.7.8"
default-features = false
[dependencies.snarkvm-utilities]
version = "0.7.4"
version = "0.7.6"
[dependencies.bincode]
version = "1.3"
@ -119,7 +119,7 @@ version = "0.3"
default-features = false
[dev-dependencies.snarkvm-algorithms]
version = "0.7.4"
version = "0.7.6"
default-features = false
[dev-dependencies.tempfile]

View File

@ -18,12 +18,7 @@
use crate::{
constraints::{generate_constraints, generate_test_constraints},
errors::CompilerError,
AstSnapshotOptions,
CompilerOptions,
GroupType,
Output,
OutputFile,
TypeInferencePhase,
AstSnapshotOptions, CompilerOptions, GroupType, Output, OutputFile, TypeInferencePhase,
};
pub use leo_asg::{new_context, AsgContext as Context, AsgContext};
use leo_asg::{Asg, AsgPass, FormattedError, Program as AsgProgram};
@ -181,7 +176,7 @@ impl<'a, F: PrimeField, G: GroupType<F>> Compiler<'a, F, G> {
state_string: &str,
state_path: &Path,
) -> Result<(), CompilerError> {
let input_syntax_tree = LeoInputParser::parse_file(&input_string).map_err(|mut e| {
let input_syntax_tree = LeoInputParser::parse_file(input_string).map_err(|mut e| {
e.set_path(
input_path.to_str().unwrap_or_default(),
&input_string.lines().map(|x| x.to_string()).collect::<Vec<String>>()[..],
@ -189,7 +184,7 @@ impl<'a, F: PrimeField, G: GroupType<F>> Compiler<'a, F, G> {
e
})?;
let state_syntax_tree = LeoInputParser::parse_file(&state_string).map_err(|mut e| {
let state_syntax_tree = LeoInputParser::parse_file(state_string).map_err(|mut e| {
e.set_path(
state_path.to_str().unwrap_or_default(),
&state_string.lines().map(|x| x.to_string()).collect::<Vec<String>>()[..],
@ -306,14 +301,14 @@ impl<'a, F: PrimeField, G: GroupType<F>> Compiler<'a, F, G> {
/// Synthesizes the circuit with program input to verify correctness.
///
pub fn compile_constraints<CS: ConstraintSystem<F>>(&self, cs: &mut CS) -> Result<Output, CompilerError> {
generate_constraints::<F, G, CS>(cs, &self.asg.as_ref().unwrap(), &self.program_input)
generate_constraints::<F, G, CS>(cs, self.asg.as_ref().unwrap(), &self.program_input)
}
///
/// Synthesizes the circuit for test functions with program input.
///
pub fn compile_test_constraints(self, input_pairs: InputPairs) -> Result<(u32, u32), CompilerError> {
generate_test_constraints::<F, G>(&self.asg.as_ref().unwrap(), input_pairs, &self.output_directory)
generate_test_constraints::<F, G>(self.asg.as_ref().unwrap(), input_pairs, &self.output_directory)
}
///

View File

@ -17,11 +17,7 @@
//! Enforces an assert equals statement in a compiled Leo program.
use crate::{
errors::ConsoleError,
get_indicator_value,
program::ConstrainedProgram,
value::ConstrainedValue,
GroupType,
errors::ConsoleError, get_indicator_value, program::ConstrainedProgram, value::ConstrainedValue, GroupType,
};
use leo_asg::{Expression, Span};

View File

@ -44,7 +44,7 @@ pub fn generate_constraints<'a, F: PrimeField, G: GroupType<F>, CS: ConstraintSy
match main {
Some(function) => {
let result = resolved_program.enforce_main_function(cs, &function, input)?;
let result = resolved_program.enforce_main_function(cs, function, input)?;
Ok(result)
}
_ => Err(CompilerError::NoMainFunction),

View File

@ -15,14 +15,7 @@
// along with the Leo library. If not, see <https://www.gnu.org/licenses/>.
use crate::errors::{
AddressError,
BooleanError,
CharError,
FieldError,
FunctionError,
GroupError,
IntegerError,
ValueError,
AddressError, BooleanError, CharError, FieldError, FunctionError, GroupError, IntegerError, ValueError,
};
use leo_ast::{FormattedError, Identifier, LeoError, Span};
use snarkvm_r1cs::SynthesisError;

View File

@ -15,16 +15,8 @@
// along with the Leo library. If not, see <https://www.gnu.org/licenses/>.
use crate::errors::{
AddressError,
BooleanError,
CharError,
ExpressionError,
FieldError,
GroupError,
IntegerError,
OutputBytesError,
StatementError,
ValueError,
AddressError, BooleanError, CharError, ExpressionError, FieldError, GroupError, IntegerError, OutputBytesError,
StatementError, ValueError,
};
use leo_asg::AsgConvertError;
use leo_ast::{FormattedError, LeoError, Span};

View File

@ -94,7 +94,7 @@ impl<'a, F: PrimeField, G: GroupType<F>> ConstrainedProgram<'a, F, G> {
.len()
.try_into()
.map_err(|_| ExpressionError::array_length_out_of_bounds(span))?;
self.array_bounds_check(cs, &&index_resolved, array_len, span)?;
self.array_bounds_check(cs, &index_resolved, array_len, span)?;
}
let mut current_value = array.pop().unwrap();

View File

@ -24,8 +24,7 @@ use crate::{
relational::*,
resolve_core_circuit,
value::{Address, Char, CharType, ConstrainedCircuitMember, ConstrainedValue, Integer},
FieldType,
GroupType,
FieldType, GroupType,
};
use leo_asg::{expression::*, ConstValue, Expression, Node, Span};

View File

@ -44,7 +44,7 @@ impl<'a, F: PrimeField, G: GroupType<F>> ConstrainedProgram<'a, F, G> {
};
let return_value = self
.enforce_function(&mut cs.ns(name_unique), &function, target, arguments)
.enforce_function(&mut cs.ns(name_unique), function, target, arguments)
.map_err(|error| ExpressionError::from(Box::new(error)))?;
Ok(return_value)

View File

@ -21,16 +21,10 @@ use crate::{
errors::{FunctionError, IntegerError},
program::ConstrainedProgram,
value::{
boolean::input::bool_from_input,
char::char_from_input,
field::input::field_from_input,
group::input::group_from_input,
ConstrainedValue,
boolean::input::bool_from_input, char::char_from_input, field::input::field_from_input,
group::input::group_from_input, ConstrainedValue,
},
CharType,
FieldType,
GroupType,
Integer,
CharType, FieldType, GroupType, Integer,
};
use leo_asg::{ConstInt, Type};
use leo_ast::{Char, InputValue, Span};
@ -62,7 +56,7 @@ impl<'a, F: PrimeField, G: GroupType<F>> ConstrainedProgram<'a, F, G> {
span,
)?)),
Type::Array(type_, len) => self.allocate_array(cs, name, &*type_, *len, input_option, span),
Type::Tuple(types) => self.allocate_tuple(cs, &name, types, input_option, span),
Type::Tuple(types) => self.allocate_tuple(cs, name, types, input_option, span),
_ => unimplemented!("main function input not implemented for type {}", type_), // Should not happen.
}
}

View File

@ -39,7 +39,7 @@ impl<'a, F: PrimeField, G: GroupType<F>> ConstrainedProgram<'a, F, G> {
if let Some(asg_input) = asg_input {
let value =
self.allocate_input_keyword(cs, &function.name.borrow().span, &asg_input.container_circuit, input)?;
self.allocate_input_keyword(cs, &function.name.borrow().span, asg_input.container_circuit, input)?;
self.store(asg_input.container.borrow().id, value);
}

View File

@ -20,16 +20,8 @@ use std::cell::Cell;
use crate::{errors::StatementError, program::ConstrainedProgram, value::ConstrainedValue, GroupType};
use leo_asg::{
ArrayAccessExpression,
ArrayRangeAccessExpression,
AssignAccess,
AssignOperation,
AssignStatement,
CircuitAccessExpression,
Expression,
Node,
TupleAccessExpression,
Variable,
ArrayAccessExpression, ArrayRangeAccessExpression, AssignAccess, AssignOperation, AssignStatement,
CircuitAccessExpression, Expression, Node, TupleAccessExpression, Variable,
};
use snarkvm_fields::PrimeField;

View File

@ -17,11 +17,7 @@
//! Enforces that one return value is produced in a compiled Leo program.
use crate::{
errors::StatementError,
get_indicator_value,
program::ConstrainedProgram,
value::ConstrainedValue,
GroupType,
errors::StatementError, get_indicator_value, program::ConstrainedProgram, value::ConstrainedValue, GroupType,
};
use leo_asg::{Span, Type};
@ -82,7 +78,7 @@ impl<'a, F: PrimeField, G: GroupType<F>> ConstrainedProgram<'a, F, G> {
cs.ns(|| format!("select result {} {}:{}", i, span.line_start, span.col_start)),
&indicator,
&result,
&value,
value,
)
.map_err(|_| StatementError::select_fail(result.to_string(), value.to_string(), span))?,
);
@ -94,7 +90,7 @@ impl<'a, F: PrimeField, G: GroupType<F>> ConstrainedProgram<'a, F, G> {
if expected_return.is_unit() {
Ok(ConstrainedValue::Tuple(vec![]))
} else {
return_value.ok_or_else(|| StatementError::no_returns(&expected_return, span))
return_value.ok_or_else(|| StatementError::no_returns(expected_return, span))
}
}
}

View File

@ -158,10 +158,13 @@ impl Output {
_ => value.to_string(),
};
registers.insert(name.to_string(), OutputRegister {
type_: register_type.to_string(),
value,
});
registers.insert(
name.to_string(),
OutputRegister {
type_: register_type.to_string(),
value,
},
);
}
Ok(Output { registers })

View File

@ -21,8 +21,7 @@ use crate::errors::OutputFileError;
use std::{
borrow::Cow,
fs::{
File,
{self},
File, {self},
},
io::Write,
path::Path,

View File

@ -18,86 +18,37 @@
use indexmap::IndexMap;
use leo_asg::{
ArrayAccessExpression as AsgArrayAccessExpression,
ArrayInitExpression as AsgArrayInitExpression,
ArrayInlineExpression as AsgArrayInlineExpression,
ArrayRangeAccessExpression as AsgArrayRangeAccessExpression,
AssignAccess as AsgAssignAccess,
AssignStatement as AsgAssignStatement,
BinaryExpression as AsgBinaryExpression,
BlockStatement as AsgBlockStatement,
CallExpression as AsgCallExpression,
CastExpression as AsgCastExpression,
CharValue as AsgCharValue,
Circuit as AsgCircuit,
CircuitAccessExpression as AsgCircuitAccessExpression,
CircuitInitExpression as AsgCircuitInitExpression,
CircuitMember as AsgCircuitMember,
ConditionalStatement as AsgConditionalStatement,
ConsoleFunction as AsgConsoleFunction,
ConsoleStatement as AsgConsoleStatement,
ConstValue,
Constant as AsgConstant,
DefinitionStatement as AsgDefinitionStatement,
Expression as AsgExpression,
ExpressionStatement as AsgExpressionStatement,
Function as AsgFunction,
GroupValue as AsgGroupValue,
IterationStatement as AsgIterationStatement,
ReturnStatement as AsgReturnStatement,
Statement as AsgStatement,
TernaryExpression as AsgTernaryExpression,
TupleAccessExpression as AsgTupleAccessExpression,
TupleInitExpression as AsgTupleInitExpression,
Type as AsgType,
UnaryExpression as AsgUnaryExpression,
ArrayAccessExpression as AsgArrayAccessExpression, ArrayInitExpression as AsgArrayInitExpression,
ArrayInlineExpression as AsgArrayInlineExpression, ArrayRangeAccessExpression as AsgArrayRangeAccessExpression,
AssignAccess as AsgAssignAccess, AssignStatement as AsgAssignStatement, BinaryExpression as AsgBinaryExpression,
BlockStatement as AsgBlockStatement, CallExpression as AsgCallExpression, CastExpression as AsgCastExpression,
CharValue as AsgCharValue, Circuit as AsgCircuit, CircuitAccessExpression as AsgCircuitAccessExpression,
CircuitInitExpression as AsgCircuitInitExpression, CircuitMember as AsgCircuitMember,
ConditionalStatement as AsgConditionalStatement, ConsoleFunction as AsgConsoleFunction,
ConsoleStatement as AsgConsoleStatement, ConstValue, Constant as AsgConstant,
DefinitionStatement as AsgDefinitionStatement, Expression as AsgExpression,
ExpressionStatement as AsgExpressionStatement, Function as AsgFunction, GroupValue as AsgGroupValue,
IterationStatement as AsgIterationStatement, ReturnStatement as AsgReturnStatement, Statement as AsgStatement,
TernaryExpression as AsgTernaryExpression, TupleAccessExpression as AsgTupleAccessExpression,
TupleInitExpression as AsgTupleInitExpression, Type as AsgType, UnaryExpression as AsgUnaryExpression,
VariableRef as AsgVariableRef,
};
use leo_ast::{
ArrayAccessExpression as AstArrayAccessExpression,
ArrayDimensions,
ArrayInitExpression as AstArrayInitExpression,
ArrayInlineExpression as AstArrayInlineExpression,
ArrayRangeAccessExpression as AstArrayRangeAccessExpression,
AssignStatement as AstAssignStatement,
Assignee,
AssigneeAccess as AstAssignAccess,
BinaryExpression as AstBinaryExpression,
Block as AstBlockStatement,
CallExpression as AstCallExpression,
CastExpression as AstCastExpression,
Char,
CharValue as AstCharValue,
Circuit as AstCircuit,
CircuitImpliedVariableDefinition,
CircuitInitExpression as AstCircuitInitExpression,
CircuitMember as AstCircuitMember,
CircuitMemberAccessExpression,
CircuitStaticFunctionAccessExpression,
CombinerError,
ConditionalStatement as AstConditionalStatement,
ConsoleArgs as AstConsoleArgs,
ConsoleFunction as AstConsoleFunction,
ConsoleStatement as AstConsoleStatement,
DefinitionStatement as AstDefinitionStatement,
Expression as AstExpression,
ExpressionStatement as AstExpressionStatement,
Function as AstFunction,
GroupTuple,
GroupValue as AstGroupValue,
IterationStatement as AstIterationStatement,
PositiveNumber,
ReconstructingReducer,
ReducerError,
ReturnStatement as AstReturnStatement,
Span,
SpreadOrExpression,
Statement as AstStatement,
TernaryExpression as AstTernaryExpression,
TupleAccessExpression as AstTupleAccessExpression,
TupleInitExpression as AstTupleInitExpression,
Type as AstType,
UnaryExpression as AstUnaryExpression,
ArrayAccessExpression as AstArrayAccessExpression, ArrayDimensions, ArrayInitExpression as AstArrayInitExpression,
ArrayInlineExpression as AstArrayInlineExpression, ArrayRangeAccessExpression as AstArrayRangeAccessExpression,
AssignStatement as AstAssignStatement, Assignee, AssigneeAccess as AstAssignAccess,
BinaryExpression as AstBinaryExpression, Block as AstBlockStatement, CallExpression as AstCallExpression,
CastExpression as AstCastExpression, Char, CharValue as AstCharValue, Circuit as AstCircuit,
CircuitImpliedVariableDefinition, CircuitInitExpression as AstCircuitInitExpression,
CircuitMember as AstCircuitMember, CircuitMemberAccessExpression, CircuitStaticFunctionAccessExpression,
CombinerError, ConditionalStatement as AstConditionalStatement, ConsoleArgs as AstConsoleArgs,
ConsoleFunction as AstConsoleFunction, ConsoleStatement as AstConsoleStatement,
DefinitionStatement as AstDefinitionStatement, Expression as AstExpression,
ExpressionStatement as AstExpressionStatement, Function as AstFunction, GroupTuple, GroupValue as AstGroupValue,
IterationStatement as AstIterationStatement, PositiveNumber, ReconstructingReducer, ReducerError,
ReturnStatement as AstReturnStatement, Span, SpreadOrExpression, Statement as AstStatement,
TernaryExpression as AstTernaryExpression, TupleAccessExpression as AstTupleAccessExpression,
TupleInitExpression as AstTupleInitExpression, Type as AstType, UnaryExpression as AstUnaryExpression,
ValueExpression,
};
use tendril::StrTendril;
@ -155,49 +106,49 @@ impl<R: ReconstructingReducer, O: CombinerOptions> CombineAstAsgDirector<R, O> {
asg: &AsgExpression,
) -> Result<AstExpression, ReducerError> {
let new = match (ast, asg) {
(AstExpression::Value(value), AsgExpression::Constant(const_)) => self.reduce_value(&value, &const_)?,
(AstExpression::Value(value), AsgExpression::Constant(const_)) => self.reduce_value(value, const_)?,
(AstExpression::Binary(ast), AsgExpression::Binary(asg)) => {
AstExpression::Binary(self.reduce_binary(&ast, &asg)?)
AstExpression::Binary(self.reduce_binary(ast, asg)?)
}
(AstExpression::Unary(ast), AsgExpression::Unary(asg)) => {
AstExpression::Unary(self.reduce_unary(&ast, &asg)?)
AstExpression::Unary(self.reduce_unary(ast, asg)?)
}
(AstExpression::Ternary(ast), AsgExpression::Ternary(asg)) => {
AstExpression::Ternary(self.reduce_ternary(&ast, &asg)?)
AstExpression::Ternary(self.reduce_ternary(ast, asg)?)
}
(AstExpression::Cast(ast), AsgExpression::Cast(asg)) => AstExpression::Cast(self.reduce_cast(&ast, &asg)?),
(AstExpression::Cast(ast), AsgExpression::Cast(asg)) => AstExpression::Cast(self.reduce_cast(ast, asg)?),
(AstExpression::ArrayInline(ast), AsgExpression::ArrayInline(asg)) => {
AstExpression::ArrayInline(self.reduce_array_inline(&ast, &asg)?)
AstExpression::ArrayInline(self.reduce_array_inline(ast, asg)?)
}
(AstExpression::ArrayInit(ast), AsgExpression::ArrayInit(asg)) => {
AstExpression::ArrayInit(self.reduce_array_init(&ast, &asg)?)
AstExpression::ArrayInit(self.reduce_array_init(ast, asg)?)
}
(AstExpression::ArrayAccess(ast), AsgExpression::ArrayAccess(asg)) => {
AstExpression::ArrayAccess(self.reduce_array_access(&ast, &asg)?)
AstExpression::ArrayAccess(self.reduce_array_access(ast, asg)?)
}
(AstExpression::ArrayRangeAccess(ast), AsgExpression::ArrayRangeAccess(asg)) => {
AstExpression::ArrayRangeAccess(self.reduce_array_range_access(&ast, &asg)?)
AstExpression::ArrayRangeAccess(self.reduce_array_range_access(ast, asg)?)
}
(AstExpression::TupleInit(ast), AsgExpression::TupleInit(asg)) => {
AstExpression::TupleInit(self.reduce_tuple_init(&ast, &asg)?)
AstExpression::TupleInit(self.reduce_tuple_init(ast, asg)?)
}
(AstExpression::TupleAccess(ast), AsgExpression::TupleAccess(asg)) => {
AstExpression::TupleAccess(self.reduce_tuple_access(&ast, &asg)?)
AstExpression::TupleAccess(self.reduce_tuple_access(ast, asg)?)
}
(AstExpression::CircuitInit(ast), AsgExpression::CircuitInit(asg)) => {
AstExpression::CircuitInit(self.reduce_circuit_init(&ast, &asg)?)
AstExpression::CircuitInit(self.reduce_circuit_init(ast, asg)?)
}
(AstExpression::CircuitMemberAccess(ast), AsgExpression::CircuitAccess(asg)) => {
AstExpression::CircuitMemberAccess(self.reduce_circuit_member_access(&ast, &asg)?)
AstExpression::CircuitMemberAccess(self.reduce_circuit_member_access(ast, asg)?)
}
(AstExpression::CircuitStaticFunctionAccess(ast), AsgExpression::CircuitAccess(asg)) => {
AstExpression::CircuitStaticFunctionAccess(self.reduce_circuit_static_fn_access(&ast, &asg)?)
AstExpression::CircuitStaticFunctionAccess(self.reduce_circuit_static_fn_access(ast, asg)?)
}
(AstExpression::Call(ast), AsgExpression::Call(asg)) => AstExpression::Call(self.reduce_call(&ast, &asg)?),
(AstExpression::Call(ast), AsgExpression::Call(asg)) => AstExpression::Call(self.reduce_call(ast, asg)?),
_ => ast.clone(),
};
@ -299,7 +250,7 @@ impl<R: ReconstructingReducer, O: CombinerOptions> CombineAstAsgDirector<R, O> {
ast: &AstCastExpression,
asg: &AsgCastExpression,
) -> Result<AstCastExpression, ReducerError> {
let inner = self.reduce_expression(&ast.inner, &asg.inner.get())?;
let inner = self.reduce_expression(&ast.inner, asg.inner.get())?;
let target_type = self.reduce_type(&ast.target_type, &asg.target_type, &ast.span)?;
self.ast_reducer.reduce_cast(ast, inner, target_type)
@ -524,7 +475,7 @@ impl<R: ReconstructingReducer, O: CombinerOptions> CombineAstAsgDirector<R, O> {
AstAssignAccess::ArrayRange(left, right)
}
(AstAssignAccess::ArrayIndex(ast_index), AsgAssignAccess::ArrayIndex(asg_index)) => {
let index = self.reduce_expression(&ast_index, asg_index.get())?;
let index = self.reduce_expression(ast_index, asg_index.get())?;
AstAssignAccess::ArrayIndex(index)
}
_ => ast.clone(),
@ -577,7 +528,7 @@ impl<R: ReconstructingReducer, O: CombinerOptions> CombineAstAsgDirector<R, O> {
block = self.reduce_block(&ast.block, asg_block)?;
} else {
return Err(ReducerError::from(CombinerError::asg_statement_not_block(
&asg.span.as_ref().unwrap(),
asg.span.as_ref().unwrap(),
)));
}
let next = match (ast.next.as_ref(), asg.next.get()) {
@ -595,7 +546,7 @@ impl<R: ReconstructingReducer, O: CombinerOptions> CombineAstAsgDirector<R, O> {
) -> Result<AstConsoleStatement, ReducerError> {
let function = match (&ast.function, &asg.function) {
(AstConsoleFunction::Assert(ast_expression), AsgConsoleFunction::Assert(asg_expression)) => {
AstConsoleFunction::Assert(self.reduce_expression(&ast_expression, asg_expression.get())?)
AstConsoleFunction::Assert(self.reduce_expression(ast_expression, asg_expression.get())?)
}
(AstConsoleFunction::Error(ast_console_args), AsgConsoleFunction::Error(asg_format))
| (AstConsoleFunction::Log(ast_console_args), AsgConsoleFunction::Log(asg_format)) => {
@ -603,7 +554,7 @@ impl<R: ReconstructingReducer, O: CombinerOptions> CombineAstAsgDirector<R, O> {
for (ast_parameter, asg_parameter) in
ast_console_args.parameters.iter().zip(asg_format.parameters.iter())
{
parameters.push(self.reduce_expression(&ast_parameter, asg_parameter.get())?);
parameters.push(self.reduce_expression(ast_parameter, asg_parameter.get())?);
}
let args = AstConsoleArgs {
@ -640,14 +591,14 @@ impl<R: ReconstructingReducer, O: CombinerOptions> CombineAstAsgDirector<R, O> {
let asg_type = AsgType::Tuple(types);
type_ = match &ast.type_ {
Some(ast_type) => Some(self.reduce_type(&ast_type, &asg_type, &ast.span)?),
Some(ast_type) => Some(self.reduce_type(ast_type, &asg_type, &ast.span)?),
None if self.options.type_inference_enabled() => Some((&asg_type).into()),
_ => None,
};
} else {
type_ = match &ast.type_ {
Some(ast_type) => {
Some(self.reduce_type(&ast_type, &asg.variables.first().unwrap().borrow().type_, &ast.span)?)
Some(self.reduce_type(ast_type, &asg.variables.first().unwrap().borrow().type_, &ast.span)?)
}
None if self.options.type_inference_enabled() => {
Some((&asg.variables.first().unwrap().borrow().type_).into())
@ -683,7 +634,7 @@ impl<R: ReconstructingReducer, O: CombinerOptions> CombineAstAsgDirector<R, O> {
block = self.reduce_block(&ast.block, asg_block)?;
} else {
return Err(ReducerError::from(CombinerError::asg_statement_not_block(
&asg.span.as_ref().unwrap(),
asg.span.as_ref().unwrap(),
)));
}

View File

@ -20,10 +20,7 @@ use leo_asg::{Function, Span};
use snarkvm_fields::PrimeField;
use snarkvm_gadgets::{
algorithms::prf::Blake2sGadget,
bits::ToBytesGadget,
integers::uint::UInt8,
traits::algorithms::PRFGadget,
algorithms::prf::Blake2sGadget, bits::ToBytesGadget, integers::uint::UInt8, traits::algorithms::PRFGadget,
};
use snarkvm_r1cs::ConstraintSystem;

View File

@ -22,8 +22,7 @@ use crate::{
errors::{ExpressionError, StatementError},
program::ConstrainedProgram,
value::ConstrainedValue,
GroupType,
Integer,
GroupType, Integer,
};
use leo_asg::{ConstInt, Expression, Node};
@ -69,7 +68,7 @@ impl<'a, F: PrimeField, G: GroupType<F>> ConstrainedProgram<'a, F, G> {
.len()
.try_into()
.map_err(|_| ExpressionError::array_length_out_of_bounds(&span))?;
self.array_bounds_check(cs, &&index_resolved, array_len, &span)?;
self.array_bounds_check(cs, &index_resolved, array_len, &span)?;
}
for (i, item) in input.iter_mut().enumerate() {
@ -116,7 +115,7 @@ impl<'a, F: PrimeField, G: GroupType<F>> ConstrainedProgram<'a, F, G> {
unique_namespace,
&index_comparison,
&temp_item,
&item,
item,
)
.map_err(|e| ExpressionError::cannot_enforce("conditional select".to_string(), e, &span))?;
*item = value;
@ -153,7 +152,7 @@ impl<'a, F: PrimeField, G: GroupType<F>> ConstrainedProgram<'a, F, G> {
.len()
.try_into()
.map_err(|_| ExpressionError::array_length_out_of_bounds(&span))?;
self.array_bounds_check(cs, &&index_resolved, array_len, &span)?;
self.array_bounds_check(cs, &index_resolved, array_len, &span)?;
}
for (i, item) in context.input.iter_mut().enumerate() {
@ -197,7 +196,7 @@ impl<'a, F: PrimeField, G: GroupType<F>> ConstrainedProgram<'a, F, G> {
item
};
let value =
ConstrainedValue::conditionally_select(unique_namespace, &index_comparison, &temp_item, &item)
ConstrainedValue::conditionally_select(unique_namespace, &index_comparison, &temp_item, item)
.map_err(|e| ExpressionError::cannot_enforce("conditional select".to_string(), e, &span))?;
**item = value;
}

View File

@ -95,15 +95,18 @@ impl<'a, F: PrimeField, G: GroupType<F>> ConstrainedProgram<'a, F, G> {
let mut target = self.get(variable.id).unwrap().clone();
let accesses: Vec<_> = assignee.target_accesses.iter().rev().collect();
self.resolve_target_access(cs, ResolverContext {
input: vec![&mut target],
span,
target_value,
remaining_accesses: &accesses[..],
indicator,
operation: assignee.operation,
from_range: false,
})?;
self.resolve_target_access(
cs,
ResolverContext {
input: vec![&mut target],
span,
target_value,
remaining_accesses: &accesses[..],
indicator,
operation: assignee.operation,
from_range: false,
},
)?;
*self.get_mut(variable.id).unwrap() = target;
Ok(())
}

View File

@ -17,12 +17,8 @@
//! Methods to enforce constraints on statements in a compiled Leo program.
use crate::{
errors::StatementError,
program::ConstrainedProgram,
value::ConstrainedValue,
GroupType,
IndicatorAndConstrainedValue,
StatementResult,
errors::StatementError, program::ConstrainedProgram, value::ConstrainedValue, GroupType,
IndicatorAndConstrainedValue, StatementResult,
};
use leo_asg::ConditionalStatement;
@ -91,7 +87,7 @@ impl<'a, F: PrimeField, G: GroupType<F>> ConstrainedProgram<'a, F, G> {
);
let branch_2_indicator = Boolean::and(
&mut cs.ns(|| format!("branch 2 {}:{}", &span.line_start, &span.col_start)),
&outer_indicator,
outer_indicator,
&inner_indicator,
)
.map_err(|_| StatementError::indicator_calculation(branch_2_name, &span))?;

View File

@ -17,14 +17,8 @@
//! Enforces an iteration statement in a compiled Leo program.
use crate::{
errors::StatementError,
program::ConstrainedProgram,
value::ConstrainedValue,
GroupType,
IndicatorAndConstrainedValue,
Integer,
IntegerTrait,
StatementResult,
errors::StatementError, program::ConstrainedProgram, value::ConstrainedValue, GroupType,
IndicatorAndConstrainedValue, Integer, IntegerTrait, StatementResult,
};
use leo_asg::IterationStatement;

View File

@ -27,11 +27,7 @@ use serde_yaml::Value;
use snarkvm_curves::{bls12_377::Bls12_377, edwards_bls12::Fq};
use crate::{
compiler::Compiler,
errors::CompilerError,
targets::edwards_bls12::EdwardsGroupType,
AstSnapshotOptions,
Output,
compiler::Compiler, errors::CompilerError, targets::edwards_bls12::EdwardsGroupType, AstSnapshotOptions, Output,
};
pub type EdwardsTestCompiler = Compiler<'static, Fq, EdwardsGroupType>;
@ -70,8 +66,9 @@ fn hash(input: String) -> String {
pub(crate) fn parse_program(
program_string: &str,
theorem_options: Option<AstSnapshotOptions>,
cwd: Option<PathBuf>,
) -> Result<EdwardsTestCompiler, CompilerError> {
let mut compiler = new_compiler("compiler-test".into(), theorem_options);
let mut compiler = new_compiler(cwd.unwrap_or("compiler-test".into()), theorem_options);
compiler.parse_program_from_string(program_string)?;
@ -105,15 +102,12 @@ impl Namespace for CompileNamespace {
// ``` cwd: import ```
// When set, uses different working directory for current file.
// If not, uses file path as current working directory.
// let cwd = test
// .config
// .get("cwd")
// .map(|val| {
// let mut cwd = test.path.clone();
// cwd.pop();
// cwd.join(&val.as_str().unwrap())
// })
// .unwrap_or(test.path.clone());
let cwd = test.config.get("cwd").map(|val| {
let mut cwd = test.path.clone();
cwd.pop();
cwd.join(&val.as_str().unwrap())
});
// .unwrap_or(test.path.clone());
let parsed = parse_program(
&test.content,
@ -122,6 +116,7 @@ impl Namespace for CompileNamespace {
canonicalized: true,
type_inferenced: true,
}),
cwd,
)
.map_err(|x| x.to_string())?;

View File

@ -85,33 +85,57 @@ impl Address {
Ok(ConstrainedValue::Address(address))
}
pub(crate) fn alloc_helper<Fn: FnOnce() -> Result<T, SynthesisError>, T: Borrow<String>>(
pub(crate) fn alloc_helper<
F: PrimeField,
CS: ConstraintSystem<F>,
Fn: FnOnce() -> Result<T, SynthesisError>,
T: Borrow<String>,
>(
cs: CS,
value_gen: Fn,
) -> Result<AleoAddress<Components>, SynthesisError> {
let address_string = match value_gen() {
Ok(value) => {
let string_value = value.borrow().clone();
Ok(string_value)
}
_ => Err(SynthesisError::AssignmentMissing),
}?;
AleoAddress::from_str(&address_string).map_err(|_| SynthesisError::AssignmentMissing)
if cs.is_in_setup_mode() {
Ok(AleoAddress::<Components>::default())
} else {
let address_string = value_gen()?.borrow().clone();
AleoAddress::from_str(&address_string).map_err(|_| SynthesisError::AssignmentMissing)
}
}
}
impl<F: PrimeField> AllocGadget<String, F> for Address {
fn alloc<Fn: FnOnce() -> Result<T, SynthesisError>, T: Borrow<String>, CS: ConstraintSystem<F>>(
cs: CS,
fn alloc_constant<Fn: FnOnce() -> Result<T, SynthesisError>, T: Borrow<String>, CS: ConstraintSystem<F>>(
_cs: CS,
value_gen: Fn,
) -> Result<Self, SynthesisError> {
let address = Self::alloc_helper(value_gen)?;
let address = {
let address_string = value_gen()?.borrow().clone();
AleoAddress::from_str(&address_string).map_err(|_| SynthesisError::AssignmentMissing)?
};
let mut address_bytes = vec![];
address
.write_le(&mut address_bytes)
.map_err(|_| SynthesisError::AssignmentMissing)?;
let bytes = UInt8::alloc_vec(cs, &address_bytes[..])?;
let bytes = UInt8::constant_vec(&address_bytes[..]);
Ok(Address {
address: Some(address),
bytes,
})
}
fn alloc<Fn: FnOnce() -> Result<T, SynthesisError>, T: Borrow<String>, CS: ConstraintSystem<F>>(
mut cs: CS,
value_gen: Fn,
) -> Result<Self, SynthesisError> {
let address = Self::alloc_helper(cs.ns(|| "allocate the address"), value_gen)?;
let mut address_bytes = vec![];
address
.write_le(&mut address_bytes)
.map_err(|_| SynthesisError::AssignmentMissing)?;
let bytes = UInt8::alloc_vec(cs.ns(|| "allocate the address bytes"), &address_bytes[..])?;
Ok(Address {
address: Some(address),
@ -120,16 +144,16 @@ impl<F: PrimeField> AllocGadget<String, F> for Address {
}
fn alloc_input<Fn: FnOnce() -> Result<T, SynthesisError>, T: Borrow<String>, CS: ConstraintSystem<F>>(
cs: CS,
mut cs: CS,
value_gen: Fn,
) -> Result<Self, SynthesisError> {
let address = Self::alloc_helper(value_gen)?;
let address = Self::alloc_helper(cs.ns(|| "allocate the address"), value_gen)?;
let mut address_bytes = vec![];
address
.write_le(&mut address_bytes)
.map_err(|_| SynthesisError::AssignmentMissing)?;
let bytes = UInt8::alloc_input_vec_le(cs, &address_bytes[..])?;
let bytes = UInt8::alloc_input_vec_le(cs.ns(|| "allocate the address bytes"), &address_bytes[..])?;
Ok(Address {
address: Some(address),
@ -200,7 +224,11 @@ impl<F: PrimeField> ConditionalEqGadget<F> for Address {
}
fn cond_select_helper(first: &Address, second: &Address, cond: bool) -> Address {
if cond { first.clone() } else { second.clone() }
if cond {
first.clone()
} else {
second.clone()
}
}
impl<F: PrimeField> CondSelectGadget<F> for Address {

View File

@ -17,8 +17,7 @@
use crate::{
errors::CharError,
value::{field::input::allocate_field, ConstrainedValue},
FieldType,
GroupType,
FieldType, GroupType,
};
use leo_ast::{InputValue, Span};

View File

@ -20,8 +20,7 @@ use leo_asg::{GroupCoordinate, GroupValue, Span};
use snarkvm_curves::{
edwards_bls12::{EdwardsAffine, EdwardsParameters, Fq},
templates::twisted_edwards_extended::Affine,
AffineCurve,
TwistedEdwardsParameters,
AffineCurve, TwistedEdwardsParameters,
};
use snarkvm_fields::{Fp256, One, Zero};
use snarkvm_gadgets::{
@ -479,7 +478,11 @@ impl CondSelectGadget<Fq> for EdwardsGroupType {
second: &Self,
) -> Result<Self, SynthesisError> {
if let Boolean::Constant(cond) = *cond {
if cond { Ok(first.clone()) } else { Ok(second.clone()) }
if cond {
Ok(first.clone())
} else {
Ok(second.clone())
}
} else {
let first_gadget = first.allocated(cs.ns(|| "first"))?;
let second_gadget = second.allocated(cs.ns(|| "second"))?;

View File

@ -124,7 +124,7 @@ impl<'a, F: PrimeField, G: GroupType<F>> fmt::Display for ConstrainedValue<'a, F
write!(f, "({})", values)
}
ConstrainedValue::CircuitExpression(ref circuit, ref members) => {
ConstrainedValue::CircuitExpression(circuit, ref members) => {
write!(f, "{} {{", circuit.name.borrow())?;
for (i, member) in members.iter().enumerate() {
write!(f, "{}: {}", member.0, member.1)?;

BIN
docs/compiler-phases.pdf Normal file

Binary file not shown.

View File

@ -0,0 +1,284 @@
# Leo RFC 009: Conversions with Bits and Bytes
## Authors
- Max Bruce
- Collin Chin
- Alessandro Coglio
- Eric McCarthy
- Jon Pavlik
- Damir Shamanaev
- Damon Sicore
- Howard Wu
## Status
DRAFT
# Summary
This RFC proposes the addition of natively implemented global functions to perform conversions
between Leo integer values and sequences of bits or bytes in big endian or little endian order.
This RFC also proposes a future transition from these functions to methods associated to the integer types.
# Motivation
Conversions of integers to bits and bytes are fairly common in programming languages.
Use case include communication with the external world
(since external data is sometimes represented as bits and bytes rather than higher-level data structures),
and serialization/deserialization for cryptographic purposes (e.g. hashing data).
# Design
## Concepts
The Leo integer values can be thought of sequences of bits.
Therefore, it makes sense to convert between integer values and their corresponding sequences of bits;
the sequences of bits can be in little or big endian order (i.e. least vs. most significant bit first),
naturally leading to two possible conversions.
Obviously, the bits represent the integers in base 2.
Since all the Leo integer values consist of multiples of 8 bits,
it also makes sense to convert between integer values and squences of bytes,
which represents the integers in base 256.
Again, the bytes may be in little or big endian order.
It could also make sense to convert between integers consisting of `N` bits
and sequences of "words" of `M` bits if `N` is a multiple of `M`,
e.g. convert a `u32` into a sequence of two `u16`s, or convert a `u128` into a sequence of four `u32`s.
However, the case in which `M` is 1 (bits) or 8 (bytes) is by far the most common,
and therefore the initial focus of this RFC;
nonetheless, it seems valuable to keep these possible generalizations in mind as we work though this initial design.
Another possible generalization is to lift these conversions to sequences,
e.g. converting from a sequence of integer values to a sequence of bits or bytes
by concatenating the results of converting the integer values,
and converting from a sequence of bits or bytes to a sequence of integer values
by grouping the bits or bytes into chunks and converting each chunk into an integer.
For instance, a sequence of 4 `u32` values can be turned into a sequence of 32 bytes or a sequence of 128 bits.
Note that, in these cases, the endianness only applies to the individual element conversion,
not to the ordering of the integer values, which should be preserved by the conversion.
Besides integers, it could make sense to consider converting other Leo values between bits and bytes,
namely characters, field elements, group elements, and addresses (but perhaps not booleans).
If this is further extended to aggregate values (tuples, arrays, and circuits),
then this moves towards a general serialization/deserialization library for Leo, which could be a separate feature.
## Representation of Bits
In Leo's current type system, bits can be represented as `bool` values.
These are not quite the numbers 0 and 1, but they are isomorphic, and it is easy to convert between booleans and bits:
```ts
// convert a boolean x to a bit:
(x ? 1 : 0)
// convert f bit y to a boolean:
(y == 1)
```
If Leo had a type `u1` for unsigned 1-bit integers, we could use that instead of `bool`.
Separately from this RFC, such a type could be added.
There is also an outstanding proposal (not in an RFC currently) to support types `uN` and `iN` for every positive `N`,
in which case `u1` would be an instance of that.
## Representation of Bytes
The type `u8` is the natural way to represent a byte.
The type `i8` is isomorphic to that, but we tend to think of bytes as unsigned.
## Representation of Sequences
This applies to the sequence of bits or bytes that a Leo integer converts to or from.
E.g. a `u32` is converted to/from a sequence of bits or bytes.
Sequences in Leo may be ntaurally represented as arrays or tuples.
Arrays are more flexible; in particular, they allow indexing via expressions rather than just numbers, unlike tuples.
Thus, arrays are the natural choice to represent these sequences.
## Conversion Functions
We propose the following global functions,
for which we write declarations without bodies below,
since the implementation is native.
(It is a separate issue whether the syntax below should be allowed,
in order to represent natively implemented functions,
or whether there should be a more explicit indication such as `native` in Java).
These are tentative names, which we can tweak.
What is more important is the selection of operations, and their input/output types.
### Conversions between Integers and Bits
```ts
// unsigned to bits, little and big endian
function u8_to_bits_le(x: u8) -> [bool; 8];
function u8_to_bits_be(x: u8) -> [bool; 8];
function u16_to_bits_le(x: u16) -> [bool; 16];
function u16_to_bits_be(x: u16) -> [bool; 16];
function u32_to_bits_le(x: u32) -> [bool; 32];
function u32_to_bits_be(x: u32) -> [bool; 32];
function u64_to_bits_le(x: u64) -> [bool; 64];
function u64_to_bits_be(x: u64) -> [bool; 64];
function u128_to_bits_le(x: u128) -> [bool; 128];
function u128_to_bits_be(x: u128) -> [bool; 128];
// signed to bits, little and big endian
function i8_to_bits_le(x: i8) -> [bool; 8];
function i8_to_bits_be(x: i8) -> [bool; 8];
function i16_to_bits_le(x: i16) -> [bool; 16];
function i16_to_bits_be(x: i16) -> [bool; 16];
function i32_to_bits_le(x: i32) -> [bool; 32];
function i32_to_bits_be(x: i32) -> [bool; 32];
function i64_to_bits_le(x: i64) -> [bool; 64];
function i64_to_bits_be(x: i64) -> [bool; 64];
function i128_to_bits_le(x: i128) -> [bool; 128];
function i128_to_bits_be(x: i128) -> [bool; 128];
// unsigned from bits, little and big endian
function u8_from_bits_le(x: [bool; 8]) -> u8;
function u8_from_bits_be(x: [bool; 8]) -> u8;
function u16_from_bits_le(x: [bool; 16]) -> u16;
function u16_from_bits_be(x: [bool; 16]) -> u16;
function u32_from_bits_le(x: [bool; 32]) -> u32;
function u32_from_bits_be(x: [bool; 32]) -> u32;
function u64_from_bits_le(x: [bool; 64]) -> u64;
function u64_from_bits_be(x: [bool; 64]) -> u64;
function u128_from_bits_le(x: [bool; 128]) -> u128;
function u128_from_bits_be(x: [bool; 128]) -> u128;
// signed from bits, little and big endian
function i8_from_bits_le(x: [bool; 8]) -> i8;
function i8_from_bits_be(x: [bool; 8]) -> i8;
function i16_from_bits_le(x: [bool; 16]) -> i16;
function i16_from_bits_be(x: [bool; 16]) -> i16;
function i32_from_bits_le(x: [bool; 32]) -> i32;
function i32_from_bits_be(x: [bool; 32]) -> i32;
function i64_from_bits_le(x: [bool; 64]) -> i64;
function i64_from_bits_be(x: [bool; 64]) -> i64;
function i128_from_bits_le(x: [bool; 128]) -> i128;
function i128_from_bits_be(x: [bool; 128]) -> i128;
```
### Conversions between Integers and Bytes
```ts
// unsigned to bytes, little and big endian
function u16_to_bytes_le(x: u16) -> [u8; 2];
function u16_to_bytes_be(x: u16) -> [u8; 2];
function u32_to_bytes_le(x: u32) -> [u8; 4];
function u32_to_bytes_be(x: u32) -> [u8; 4];
function u64_to_bytes_le(x: u64) -> [u8; 8];
function u64_to_bytes_be(x: u64) -> [u8; 8];
function u128_to_bytes_le(x: u128) -> [u8; 16];
function u128_to_bytes_be(x: u128) -> [u8; 16];
// signed to bytes, little and big endian
function i16_to_bytes_le(x: i16) -> [u8; 2];
function i16_to_bytes_be(x: i16) -> [u8; 2];
function i32_to_bytes_le(x: i32) -> [u8; 4];
function i32_to_bytes_be(x: i32) -> [u8; 4];
function i64_to_bytes_le(x: i64) -> [u8; 8];
function i64_to_bytes_be(x: i64) -> [u8; 8];
function i128_to_bytes_le(x: i128) -> [u8; 16];
function i128_to_bytes_be(x: i128) -> [u8; 16];
// unsigned from bytes, little and big endian
function u16_from_bytes_le(x: [u8; 2]) -> u16;
function u16_from_bytes_be(x: [u8; 2]) -> u16;
function u32_from_bytes_le(x: [u8; 4]) -> u32;
function u32_from_bytes_be(x: [u8; 4]) -> u32;
function u64_from_bytes_le(x: [u8; 8]) -> u64;
function u64_from_bytes_be(x: [u8; 8]) -> u64;
function u128_from_bytes_le(x: [u8; 16]) -> u128;
function u128_from_bytes_be(x: [u8; 16]) -> u128;
// signed from bytes, little and big endian
function i16_from_bytes_le(x: [u8; 2]) -> i16;
function i16_from_bytes_be(x: [u8; 2]) -> i16;
function i32_from_bytes_le(x: [u8; 4]) -> i32;
function i32_from_bytes_be(x: [u8; 4]) -> i32;
function i64_from_bytes_le(x: [u8; 8]) -> i64;
function i64_from_bytes_be(x: [u8; 8]) -> i64;
function i128_from_bytes_le(x: [u8; 16]) -> i128;
function i128_from_bytes_be(x: [u8; 16]) -> i128;
```
## Handling of the Native Functions
Given the relatively large number and regular structure of the functions above,
it makes sense to generate them programmatically (e.g. via Rust macros),
rather than enumerating all of them explicitly in the implementation.
It may also makes sense, at R1CS generation time,
to use generated or suitably parameterized code to recognize them and turn them into the corresponding gadgets.
## Transition to Methods
Once a separate proposal for adding methods to Leo scalar types is realized,
we may want to turn the global functions listed above into methods,
deprecating the global functions, and eventually eliminating them.
Conversions to bits or bytes will be instance methods of the integer types,
e.g. `u8` will include an instance method `to_bits_le` that takes no arguments and that returns a `[bool; 8]`.
Example:
```ts
let int: u8 = 12;
let bits: [bool; 8] = int.to_bits_le();
console.assert(bits == [false, false, true, true, false, false, false, false]); // 00110000 (little endian)
```
Conversions from bits or bytes will be static methods of the integer types,
e.g. `u8` will include a static metod `from_bits_le` that takes a `[bool; 8]` argument and returns a `u8`.
Example:
```ts
let bits: [bool; 8] = [false, false, true, true, false, false, false, false]; // 00110000 (little endian)
let int = u8::from_bits_le(bits);
console.assert(int == 12);
```
# Drawbacks
This does not seem to bring any drawbacks.
# Effect on Ecosystem
None.
# Alternatives
## Pure Leo Implementation
These conversions can be realized in Leo (i.e. without native implementations),
provided that Leo is extended with certain operations that are already separately planned:
* Integer division and remainder, along with type casts, could be used.
* Bitwise shifts and masks, along with type casts, could be used.
However, compiling the Leo code that realizes the conversions may result in less efficient R1CS than the native ones.
## Naming Bit and Byte Types Explicitly
Names like `u8_to_bits_le` and `u32_to_bytes_le` talk about bits and bytes,
therefore relying on a choice of representation for bits and bytes,
which is `bool` for bits and `u8` for bytes as explained above.
An alternative is to have names like `u8_to_bools_le` and `u32_to_u8s_le`,
which explicate the representation of bits and bytes in the name,
and open the door to additional conversions to different representations.
In particular, if and when Leo is extended with a type `u1` for bits,
there could be additional operations like `u8_to_u1s_le`.
This more explicit naming scheme also provides a path towards extending
bit and byte conversions to more generic "word" conversions,
such as `u64_to_u16s_le`, which would turn a `u64` into a `[u16; 4]`.
In general, it makes sense to convert between `uN` or `iN` and `[uM; P]` when `N == M * P`.
If Leo were extended with types `uN` and `iN` for all positive `N` as proposed elsewhere,
there could be a family of all such conversions.
## Methods Directly
Given that we eventually plan to use methods on scalar types for these conversions,
it may make sense to do that right away.
This is predicated on having support for methods on scalar types,
for which a separate RFC is in the works.
If we decide for this approach, we will revise the above proposal to reflect that.
The concepts and (essential) names and input/output types remain unchanged,
but the conversions are packaged in slightly different form.

View File

@ -1,6 +1,6 @@
[package]
name = "leo-abnf"
version = "1.5.2"
version = "1.5.3"
authors = [ "The Aleo Team <hello@aleo.org>" ]
description = "ABNF to Markdown converter for the Leo programming language"
homepage = "https://aleo.org"

View File

@ -476,7 +476,7 @@ Line terminators form whitespace, along with spaces and horizontal tabs.
whitespace = space / horizontal-tab / newline
```
Go to: _[space](#user-content-space), [newline](#user-content-newline), [horizontal-tab](#user-content-horizontal-tab)_;
Go to: _[horizontal-tab](#user-content-horizontal-tab), [newline](#user-content-newline), [space](#user-content-space)_;
There are two kinds of comments in Leo, as in other languages.
@ -511,7 +511,7 @@ rest-of-block-comment = "*" rest-of-block-comment-after-star
/ not-star rest-of-block-comment
```
Go to: _[rest-of-block-comment](#user-content-rest-of-block-comment), [rest-of-block-comment-after-star](#user-content-rest-of-block-comment-after-star), [not-star](#user-content-not-star)_;
Go to: _[rest-of-block-comment-after-star](#user-content-rest-of-block-comment-after-star), [not-star](#user-content-not-star), [rest-of-block-comment](#user-content-rest-of-block-comment)_;
<a name="rest-of-block-comment-after-star"></a>
@ -572,13 +572,7 @@ keyword = %s"address"
/ %s"u128"
```
The following rules define (ASCII)
digits and (uppercase and lowercase) letters.
<a name="digit"></a>
```abnf
digit = %x30-39 ; 0-9
```
The following rules define (ASCII) letters.
<a name="uppercase-letter"></a>
```abnf
@ -595,12 +589,17 @@ lowercase-letter = %x61-7A ; a-z
letter = uppercase-letter / lowercase-letter
```
Go to: _[lowercase-letter](#user-content-lowercase-letter), [uppercase-letter](#user-content-uppercase-letter)_;
Go to: _[uppercase-letter](#user-content-uppercase-letter), [lowercase-letter](#user-content-lowercase-letter)_;
The following rules defines (ASCII) octal and hexadecimal digits.
The following rules defines (ASCII) decimal, octal, and hexadecimal digits.
Note that the latter are case-insensitive.
<a name="decimal-digit"></a>
```abnf
decimal-digit = %x30-39 ; 0-9
```
<a name="octal-digit"></a>
```abnf
octal-digit = %x30-37 ; 0-7
@ -608,13 +607,14 @@ octal-digit = %x30-37 ; 0-7
<a name="hexadecimal-digit"></a>
```abnf
hexadecimal-digit = digit / "a" / "b" / "c" / "d" / "e" / "f"
hexadecimal-digit = decimal-digit / "a" / "b" / "c" / "d" / "e" / "f"
```
Go to: _[digit](#user-content-digit)_;
Go to: _[decimal-digit](#user-content-decimal-digit)_;
An identifier is a non-empty sequence of letters, digits, and underscores,
An identifier is a non-empty sequence of
letters, (decimal) digits, and underscores,
starting with a letter.
It must not be a keyword: this is an extra-grammatical requirement.
It must also not be or start with `aleo1`,
@ -623,7 +623,7 @@ this is another extra-grammatical requirement.
<a name="identifier"></a>
```abnf
identifier = letter *( letter / digit / "_" )
identifier = letter *( letter / decimal-digit / "_" )
; but not a keyword or a boolean literal or aleo1...
```
@ -631,14 +631,15 @@ Go to: _[letter](#user-content-letter)_;
A package name consists of one or more segments separated by single dashes,
where each segment is a non-empty sequence of lowercase letters and digits.
where each segment is a non-empty sequence of
lowercase letters and (decimal) digits.
Similarly to an identifier, a package name must not be a keyword
and must not be or start with `aleo1`.
<a name="package-name"></a>
```abnf
package-name = lowercase-letter *( lowercase-letter / digit )
*( "-" 1*( lowercase-letter / digit ) )
package-name = lowercase-letter *( lowercase-letter / decimal-digit )
*( "-" 1*( lowercase-letter / decimal-digit ) )
; but not a keyword or a boolean literal or aleo1...
```
@ -658,12 +659,12 @@ annotation-name = "@" identifier
Go to: _[identifier](#user-content-identifier)_;
A natural (number) is a sequence of one or more digits.
A natural (number) is a sequence of one or more decimal digits.
We allow leading zeros, e.g. `007`.
<a name="natural"></a>
```abnf
natural = 1*digit
natural = 1*decimal-digit
```
An integer (number) is either a natural or its negation.
@ -739,12 +740,12 @@ boolean-literal = %s"true" / %s"false"
```
An address literal starts with `aleo1`
and continues with exactly 58 lowercase letters and digits.
and continues with exactly 58 lowercase letters and (decimal) digits.
Thus an address always consists of 63 characters.
<a name="address-literal"></a>
```abnf
address-literal = %s"aleo1" 58( lowercase-letter / digit )
address-literal = %s"aleo1" 58( lowercase-letter / decimal-digit )
```
A character literal consists of an element surrounded by single quotes.
@ -772,7 +773,7 @@ character-literal-element = not-single-quote-or-backslash
/ unicode-character-escape
```
Go to: _[simple-character-escape](#user-content-simple-character-escape), [unicode-character-escape](#user-content-unicode-character-escape), [not-single-quote-or-backslash](#user-content-not-single-quote-or-backslash), [ascii-character-escape](#user-content-ascii-character-escape)_;
Go to: _[not-single-quote-or-backslash](#user-content-not-single-quote-or-backslash), [ascii-character-escape](#user-content-ascii-character-escape), [unicode-character-escape](#user-content-unicode-character-escape), [simple-character-escape](#user-content-simple-character-escape)_;
<a name="single-quote-escape"></a>
@ -827,7 +828,7 @@ simple-character-escape = single-quote-escape
/ null-character-escape
```
Go to: _[carriage-return-escape](#user-content-carriage-return-escape), [single-quote-escape](#user-content-single-quote-escape), [backslash-escape](#user-content-backslash-escape), [line-feed-escape](#user-content-line-feed-escape), [horizontal-tab-escape](#user-content-horizontal-tab-escape), [null-character-escape](#user-content-null-character-escape), [double-quote-escape](#user-content-double-quote-escape)_;
Go to: _[carriage-return-escape](#user-content-carriage-return-escape), [horizontal-tab-escape](#user-content-horizontal-tab-escape), [null-character-escape](#user-content-null-character-escape), [double-quote-escape](#user-content-double-quote-escape), [single-quote-escape](#user-content-single-quote-escape), [backslash-escape](#user-content-backslash-escape), [line-feed-escape](#user-content-line-feed-escape)_;
<a name="ascii-character-escape"></a>
@ -835,7 +836,7 @@ Go to: _[carriage-return-escape](#user-content-carriage-return-escape), [single-
ascii-character-escape = %s"\x" octal-digit hexadecimal-digit
```
Go to: _[hexadecimal-digit](#user-content-hexadecimal-digit), [octal-digit](#user-content-octal-digit)_;
Go to: _[octal-digit](#user-content-octal-digit), [hexadecimal-digit](#user-content-hexadecimal-digit)_;
<a name="unicode-character-escape"></a>
@ -863,7 +864,7 @@ string-literal-element = not-double-quote-or-backslash
/ unicode-character-escape
```
Go to: _[not-double-quote-or-backslash](#user-content-not-double-quote-or-backslash), [simple-character-escape](#user-content-simple-character-escape), [unicode-character-escape](#user-content-unicode-character-escape), [ascii-character-escape](#user-content-ascii-character-escape)_;
Go to: _[ascii-character-escape](#user-content-ascii-character-escape), [unicode-character-escape](#user-content-unicode-character-escape), [simple-character-escape](#user-content-simple-character-escape), [not-double-quote-or-backslash](#user-content-not-double-quote-or-backslash)_;
The ones above are all the atomic literals
@ -883,7 +884,7 @@ atomic-literal = untyped-literal
/ string-literal
```
Go to: _[string-literal](#user-content-string-literal), [product-group-literal](#user-content-product-group-literal), [unsigned-literal](#user-content-unsigned-literal), [field-literal](#user-content-field-literal), [address-literal](#user-content-address-literal), [boolean-literal](#user-content-boolean-literal), [untyped-literal](#user-content-untyped-literal), [character-literal](#user-content-character-literal), [signed-literal](#user-content-signed-literal)_;
Go to: _[signed-literal](#user-content-signed-literal), [untyped-literal](#user-content-untyped-literal), [product-group-literal](#user-content-product-group-literal), [unsigned-literal](#user-content-unsigned-literal), [character-literal](#user-content-character-literal), [string-literal](#user-content-string-literal), [field-literal](#user-content-field-literal), [boolean-literal](#user-content-boolean-literal), [address-literal](#user-content-address-literal)_;
After defining the (mostly) alphanumeric tokens above,
@ -927,7 +928,17 @@ token = keyword
/ symbol
```
Go to: _[atomic-literal](#user-content-atomic-literal), [identifier](#user-content-identifier), [symbol](#user-content-symbol), [package-name](#user-content-package-name), [annotation-name](#user-content-annotation-name), [keyword](#user-content-keyword)_;
Go to: _[identifier](#user-content-identifier), [keyword](#user-content-keyword), [symbol](#user-content-symbol), [package-name](#user-content-package-name), [annotation-name](#user-content-annotation-name), [atomic-literal](#user-content-atomic-literal)_;
Tokens, comments, and whitespace are lexemes, i.e. lexical units.
<a name="lexeme"></a>
```abnf
lexeme = token / comment / whitespace
```
Go to: _[whitespace](#user-content-whitespace), [token](#user-content-token), [comment](#user-content-comment)_;
@ -963,7 +974,7 @@ signed-type = %s"i8" / %s"i16" / %s"i32" / %s"i64" / %s"i128"
integer-type = unsigned-type / signed-type
```
Go to: _[unsigned-type](#user-content-unsigned-type), [signed-type](#user-content-signed-type)_;
Go to: _[signed-type](#user-content-signed-type), [unsigned-type](#user-content-unsigned-type)_;
The integer types, along with the field and group types,
@ -984,7 +995,7 @@ group-type = %s"group"
arithmetic-type = integer-type / field-type / group-type
```
Go to: _[field-type](#user-content-field-type), [group-type](#user-content-group-type), [integer-type](#user-content-integer-type)_;
Go to: _[integer-type](#user-content-integer-type), [field-type](#user-content-field-type), [group-type](#user-content-group-type)_;
The arithmetic types, along with the boolean, address, and character types,
@ -1010,7 +1021,7 @@ character-type = %s"char"
scalar-type = boolean-type / arithmetic-type / address-type / character-type
```
Go to: _[address-type](#user-content-address-type), [boolean-type](#user-content-boolean-type), [character-type](#user-content-character-type), [arithmetic-type](#user-content-arithmetic-type)_;
Go to: _[character-type](#user-content-character-type), [arithmetic-type](#user-content-arithmetic-type), [boolean-type](#user-content-boolean-type), [address-type](#user-content-address-type)_;
Circuit types are denoted by identifiers and the keyword `Self`.
@ -1071,7 +1082,7 @@ i.e. types whose values contain (sub-)values
aggregate-type = tuple-type / array-type / circuit-type
```
Go to: _[tuple-type](#user-content-tuple-type), [array-type](#user-content-array-type), [circuit-type](#user-content-circuit-type)_;
Go to: _[circuit-type](#user-content-circuit-type), [tuple-type](#user-content-tuple-type), [array-type](#user-content-array-type)_;
Scalar and aggregate types form all the types.
@ -1081,7 +1092,7 @@ Scalar and aggregate types form all the types.
type = scalar-type / aggregate-type
```
Go to: _[aggregate-type](#user-content-aggregate-type), [scalar-type](#user-content-scalar-type)_;
Go to: _[scalar-type](#user-content-scalar-type), [aggregate-type](#user-content-aggregate-type)_;
The lexical grammar given earlier defines product group literals.
@ -1117,7 +1128,7 @@ A literal is either an atomic one or an affine group literal.
literal = atomic-literal / affine-group-literal
```
Go to: _[atomic-literal](#user-content-atomic-literal), [affine-group-literal](#user-content-affine-group-literal)_;
Go to: _[affine-group-literal](#user-content-affine-group-literal), [atomic-literal](#user-content-atomic-literal)_;
The following rule is not directly referenced in the rules for expressions
@ -1130,7 +1141,7 @@ a group literal is either a product group literal or an affine group literal.
group-literal = product-group-literal / affine-group-literal
```
Go to: _[affine-group-literal](#user-content-affine-group-literal), [product-group-literal](#user-content-product-group-literal)_;
Go to: _[product-group-literal](#user-content-product-group-literal), [affine-group-literal](#user-content-affine-group-literal)_;
As often done in grammatical language syntax specifications,
@ -1159,7 +1170,7 @@ primary-expression = identifier
/ circuit-expression
```
Go to: _[tuple-expression](#user-content-tuple-expression), [literal](#user-content-literal), [expression](#user-content-expression), [circuit-expression](#user-content-circuit-expression), [identifier](#user-content-identifier), [array-expression](#user-content-array-expression)_;
Go to: _[array-expression](#user-content-array-expression), [expression](#user-content-expression), [circuit-expression](#user-content-circuit-expression), [identifier](#user-content-identifier), [tuple-expression](#user-content-tuple-expression), [literal](#user-content-literal)_;
Tuple expressions construct tuples.
@ -1248,7 +1259,7 @@ circuit-construction = circuit-type "{"
"}"
```
Go to: _[circuit-inline-element](#user-content-circuit-inline-element), [circuit-type](#user-content-circuit-type)_;
Go to: _[circuit-type](#user-content-circuit-type), [circuit-inline-element](#user-content-circuit-inline-element)_;
<a name="circuit-inline-element"></a>
@ -1307,7 +1318,7 @@ postfix-expression = primary-expression
/ postfix-expression "[" [expression] ".." [expression] "]"
```
Go to: _[circuit-type](#user-content-circuit-type), [postfix-expression](#user-content-postfix-expression), [primary-expression](#user-content-primary-expression), [identifier](#user-content-identifier), [function-arguments](#user-content-function-arguments), [natural](#user-content-natural), [expression](#user-content-expression)_;
Go to: _[identifier](#user-content-identifier), [circuit-type](#user-content-circuit-type), [function-arguments](#user-content-function-arguments), [natural](#user-content-natural), [primary-expression](#user-content-primary-expression), [expression](#user-content-expression), [postfix-expression](#user-content-postfix-expression)_;
Unary operators have the highest operator precedence.
@ -1359,7 +1370,7 @@ additive-expression = multiplicative-expression
/ additive-expression "-" multiplicative-expression
```
Go to: _[multiplicative-expression](#user-content-multiplicative-expression), [additive-expression](#user-content-additive-expression)_;
Go to: _[additive-expression](#user-content-additive-expression), [multiplicative-expression](#user-content-multiplicative-expression)_;
Next in the precedence order are ordering relations.
@ -1422,7 +1433,7 @@ conditional-expression = disjunctive-expression
":" conditional-expression
```
Go to: _[expression](#user-content-expression), [conditional-expression](#user-content-conditional-expression), [disjunctive-expression](#user-content-disjunctive-expression)_;
Go to: _[disjunctive-expression](#user-content-disjunctive-expression), [expression](#user-content-expression), [conditional-expression](#user-content-conditional-expression)_;
Those above are all the expressions.
@ -1455,7 +1466,7 @@ statement = expression-statement
/ block
```
Go to: _[assignment-statement](#user-content-assignment-statement), [expression-statement](#user-content-expression-statement), [conditional-statement](#user-content-conditional-statement), [block](#user-content-block), [loop-statement](#user-content-loop-statement), [constant-declaration](#user-content-constant-declaration), [console-statement](#user-content-console-statement), [variable-declaration](#user-content-variable-declaration), [return-statement](#user-content-return-statement)_;
Go to: _[loop-statement](#user-content-loop-statement), [assignment-statement](#user-content-assignment-statement), [variable-declaration](#user-content-variable-declaration), [expression-statement](#user-content-expression-statement), [conditional-statement](#user-content-conditional-statement), [block](#user-content-block), [console-statement](#user-content-console-statement), [return-statement](#user-content-return-statement), [constant-declaration](#user-content-constant-declaration)_;
<a name="block"></a>
@ -1498,7 +1509,7 @@ variable-declaration = %s"let" identifier-or-identifiers [ ":" type ]
"=" expression ";"
```
Go to: _[expression](#user-content-expression), [identifier-or-identifiers](#user-content-identifier-or-identifiers), [type](#user-content-type)_;
Go to: _[type](#user-content-type), [identifier-or-identifiers](#user-content-identifier-or-identifiers), [expression](#user-content-expression)_;
<a name="constant-declaration"></a>
@ -1540,7 +1551,7 @@ conditional-statement = branch
/ branch %s"else" conditional-statement
```
Go to: _[branch](#user-content-branch), [conditional-statement](#user-content-conditional-statement), [block](#user-content-block)_;
Go to: _[branch](#user-content-branch), [block](#user-content-block), [conditional-statement](#user-content-conditional-statement)_;
A loop statement implicitly defines a loop variable
@ -1638,7 +1649,7 @@ annotation = annotation-name
[ "(" identifier *( "," identifier ) ")" ]
```
Go to: _[identifier](#user-content-identifier), [annotation-name](#user-content-annotation-name)_;
Go to: _[annotation-name](#user-content-annotation-name), [identifier](#user-content-identifier)_;
A function declaration defines a function.
@ -1655,7 +1666,7 @@ function-declaration = *annotation %s"function" identifier
block
```
Go to: _[type](#user-content-type), [identifier](#user-content-identifier), [function-parameters](#user-content-function-parameters), [block](#user-content-block)_;
Go to: _[identifier](#user-content-identifier), [function-parameters](#user-content-function-parameters), [type](#user-content-type), [block](#user-content-block)_;
<a name="function-parameters"></a>
@ -1706,7 +1717,7 @@ member-variable-declarations = *( identifier ":" type ( "," / ";" ) )
identifier ":" type ( [ "," ] / ";" )
```
Go to: _[identifier](#user-content-identifier), [type](#user-content-type)_;
Go to: _[type](#user-content-type), [identifier](#user-content-identifier)_;
A circuit member function declaration consists of a function declaration.
@ -1734,7 +1745,7 @@ circuit-declaration = %s"circuit" identifier
*member-function-declaration "}"
```
Go to: _[identifier](#user-content-identifier), [member-variable-declarations](#user-content-member-variable-declarations)_;
Go to: _[member-variable-declarations](#user-content-member-variable-declarations), [identifier](#user-content-identifier)_;
An import declaration consists of the `import` keyword
@ -1767,7 +1778,7 @@ package-path = "*"
/ "(" package-path *( "," package-path ) [","] ")"
```
Go to: _[package-name](#user-content-package-name), [identifier](#user-content-identifier), [package-path](#user-content-package-path)_;
Go to: _[identifier](#user-content-identifier), [package-path](#user-content-package-path), [package-name](#user-content-package-name)_;
Finally, we define a file as a sequence of zero or more declarations.
@ -1782,7 +1793,7 @@ declaration = import-declaration
/ constant-declaration
```
Go to: _[circuit-declaration](#user-content-circuit-declaration), [constant-declaration](#user-content-constant-declaration), [import-declaration](#user-content-import-declaration), [function-declaration](#user-content-function-declaration)_;
Go to: _[function-declaration](#user-content-function-declaration), [constant-declaration](#user-content-constant-declaration), [import-declaration](#user-content-import-declaration), [circuit-declaration](#user-content-circuit-declaration)_;
<a name="file"></a>

View File

@ -421,10 +421,7 @@ keyword = %s"address"
/ %s"u64"
/ %s"u128"
; The following rules define (ASCII)
; digits and (uppercase and lowercase) letters.
digit = %x30-39 ; 0-9
; The following rules define (ASCII) letters.
uppercase-letter = %x41-5A ; A-Z
@ -432,30 +429,34 @@ lowercase-letter = %x61-7A ; a-z
letter = uppercase-letter / lowercase-letter
; The following rules defines (ASCII) octal and hexadecimal digits.
; The following rules defines (ASCII) decimal, octal, and hexadecimal digits.
; Note that the latter are case-insensitive.
decimal-digit = %x30-39 ; 0-9
octal-digit = %x30-37 ; 0-7
hexadecimal-digit = digit / "a" / "b" / "c" / "d" / "e" / "f"
hexadecimal-digit = decimal-digit / "a" / "b" / "c" / "d" / "e" / "f"
; An identifier is a non-empty sequence of letters, digits, and underscores,
; An identifier is a non-empty sequence of
; letters, (decimal) digits, and underscores,
; starting with a letter.
; It must not be a keyword: this is an extra-grammatical requirement.
; It must also not be or start with `aleo1`,
; because that is used for address literals:
; this is another extra-grammatical requirement.
identifier = letter *( letter / digit / "_" )
identifier = letter *( letter / decimal-digit / "_" )
; but not a keyword or a boolean literal or aleo1...
; A package name consists of one or more segments separated by single dashes,
; where each segment is a non-empty sequence of lowercase letters and digits.
; where each segment is a non-empty sequence of
; lowercase letters and (decimal) digits.
; Similarly to an identifier, a package name must not be a keyword
; and must not be or start with `aleo1`.
package-name = lowercase-letter *( lowercase-letter / digit )
*( "-" 1*( lowercase-letter / digit ) )
package-name = lowercase-letter *( lowercase-letter / decimal-digit )
*( "-" 1*( lowercase-letter / decimal-digit ) )
; but not a keyword or a boolean literal or aleo1...
; Note that, grammatically, identifiers are also package names.
@ -465,10 +466,10 @@ package-name = lowercase-letter *( lowercase-letter / digit )
annotation-name = "@" identifier
; A natural (number) is a sequence of one or more digits.
; A natural (number) is a sequence of one or more decimal digits.
; We allow leading zeros, e.g. `007`.
natural = 1*digit
natural = 1*decimal-digit
; An integer (number) is either a natural or its negation.
; We allow leading zeros also in negative numbers, e.g. `-007`.
@ -504,10 +505,10 @@ product-group-literal = integer %s"group"
boolean-literal = %s"true" / %s"false"
; An address literal starts with `aleo1`
; and continues with exactly 58 lowercase letters and digits.
; and continues with exactly 58 lowercase letters and (decimal) digits.
; Thus an address always consists of 63 characters.
address-literal = %s"aleo1" 58( lowercase-letter / digit )
address-literal = %s"aleo1" 58( lowercase-letter / decimal-digit )
; A character literal consists of an element surrounded by single quotes.
; The element is any character other than single quote or backslash,
@ -611,6 +612,10 @@ token = keyword
/ annotation-name
/ symbol
; Tokens, comments, and whitespace are lexemes, i.e. lexical units.
lexeme = token / comment / whitespace
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
; Syntactic Grammar

View File

@ -1,6 +1,6 @@
[package]
name = "leo-imports"
version = "1.5.2"
version = "1.5.3"
authors = [ "The Aleo Team <hello@aleo.org>" ]
description = "Import parser for Leo program package dependencies"
homepage = "https://aleo.org"
@ -19,15 +19,15 @@ edition = "2018"
[dependencies.leo-ast]
path = "../ast"
version = "1.5.2"
version = "1.5.3"
[dependencies.leo-asg]
path = "../asg"
version = "1.5.2"
version = "1.5.3"
[dependencies.leo-parser]
path = "../parser"
version = "1.5.2"
version = "1.5.3"
[dependencies.indexmap]
version = "1.7.0"

View File

@ -55,10 +55,9 @@ impl ImportResolver for ImportParser {
if let Some(program) = self.imports.get(&full_path) {
return Ok(Some(program.clone()));
}
let mut imports = Self::default();
let path = self.program_path.clone();
self.partial_imports.insert(full_path.clone());
let mut imports = self.clone(); // Self::default() was previously
let program = imports
.parse_package(path, package_segments, span)
.map_err(|x| -> ReducerError { x.into() })?;

View File

@ -54,7 +54,7 @@ impl ImportParser {
// Build the package abstract syntax tree.
let program_string =
&std::fs::read_to_string(&file_path).map_err(|x| ImportParserError::io_error(span, file_path_str, x))?;
let mut program = leo_parser::parse(&file_path_str, &program_string)?;
let mut program = leo_parser::parse(file_path_str, program_string)?;
program.name = file_name;
Ok(program)
}

View File

@ -1,6 +1,6 @@
[package]
name = "leo-input"
version = "1.5.2"
version = "1.5.3"
authors = [ "The Aleo Team <hello@aleo.org>" ]
description = "Input parser of the Leo programming language"
homepage = "https://aleo.org"

View File

@ -191,7 +191,7 @@ impl InputParserError {
expected, actual
);
Self::new_from_span(message, &span)
Self::new_from_span(message, span)
}
pub fn section(header: Header) -> Self {

View File

@ -32,7 +32,7 @@ pub enum GroupCoordinate<'ast> {
impl<'ast> GroupCoordinate<'ast> {
pub fn span(&self) -> &Span<'ast> {
match self {
GroupCoordinate::Number(number) => &number.span(),
GroupCoordinate::Number(number) => number.span(),
GroupCoordinate::SignHigh(sign_high) => &sign_high.span,
GroupCoordinate::SignLow(sign_low) => &sign_low.span,
GroupCoordinate::Inferred(inferred) => &inferred.span,

View File

@ -39,13 +39,13 @@ pub enum Value<'ast> {
impl<'ast> Value<'ast> {
pub fn span(&self) -> &Span<'ast> {
match self {
Value::Address(value) => &value.span(),
Value::Address(value) => value.span(),
Value::Boolean(value) => &value.span,
Value::Char(value) => &value.span,
Value::Field(value) => &value.span,
Value::Group(value) => &value.span,
Value::Implicit(value) => &value.span(),
Value::Integer(value) => &value.span(),
Value::Implicit(value) => value.span(),
Value::Integer(value) => value.span(),
}
}
}

View File

@ -17,8 +17,7 @@
use anyhow::{anyhow, Error, Result};
use reqwest::{
blocking::{multipart::Form, Client, Response},
Method,
StatusCode,
Method, StatusCode,
};
use serde::{Deserialize, Serialize};
use std::{collections::HashMap, path::PathBuf};

View File

@ -18,8 +18,7 @@ use crate::{commands::Command, context::Context};
use leo_compiler::{
compiler::{thread_leaked_context, Compiler},
group::targets::edwards_bls12::EdwardsGroupType,
AstSnapshotOptions,
CompilerOptions,
AstSnapshotOptions, CompilerOptions,
};
use leo_package::{
inputs::*,

View File

@ -20,8 +20,7 @@ use anyhow::{anyhow, Result};
use std::{
borrow::Cow,
fs::{
File,
{self},
File, {self},
},
io::{Read, Write},
path::Path,

View File

@ -16,9 +16,7 @@
use std::{
fs::{
create_dir_all,
File,
{self},
create_dir_all, File, {self},
},
io,
io::prelude::*,
@ -144,10 +142,10 @@ pub fn write_token_and_username(token: &str, username: &str) -> Result<(), io::E
}
let mut credentials = File::create(&LEO_CREDENTIALS_PATH.to_path_buf())?;
credentials.write_all(&token.as_bytes())?;
credentials.write_all(token.as_bytes())?;
let mut username_file = File::create(&LEO_USERNAME_PATH.to_path_buf())?;
username_file.write_all(&username.as_bytes())?;
username_file.write_all(username.as_bytes())?;
Ok(())
}

View File

@ -23,19 +23,7 @@ pub mod updater;
use commands::{
package::{Add, Clone, Login, Logout, Publish, Remove},
Build,
Clean,
Command,
Deploy,
Init,
Lint,
New,
Prove,
Run,
Setup,
Test,
Update,
Watch,
Build, Clean, Command, Deploy, Init, Lint, New, Prove, Run, Setup, Test, Update, Watch,
};
use anyhow::Result;
@ -189,10 +177,13 @@ fn main() {
fn run_with_args(opt: Opt) -> Result<()> {
if !opt.quiet {
// Init logger with optional debug flag.
logger::init_logger("leo", match opt.debug {
false => 1,
true => 2,
})?;
logger::init_logger(
"leo",
match opt.debug {
false => 1,
true => 2,
},
)?;
}
// Get custom root folder and create context for it.

View File

@ -20,14 +20,7 @@ use std::path::PathBuf;
use crate::{
commands::{
package::{Login, Logout},
Build,
Command,
Prove,
Run,
Setup,
Test,
Update,
UpdateAutomatic,
Build, Command, Prove, Run, Setup, Test, Update, UpdateAutomatic,
},
context::{create_context, Context},
};

View File

@ -53,7 +53,7 @@ impl Updater {
.repo_owner(Self::LEO_REPO_OWNER)
.repo_name(Self::LEO_REPO_NAME)
.bin_name(Self::LEO_BIN_NAME)
.current_version(&env!("CARGO_PKG_VERSION"))
.current_version(env!("CARGO_PKG_VERSION"))
.show_download_progress(show_output)
.no_confirm(true)
.show_output(show_output)
@ -69,7 +69,7 @@ impl Updater {
.repo_owner(Self::LEO_REPO_OWNER)
.repo_name(Self::LEO_REPO_NAME)
.bin_name(Self::LEO_BIN_NAME)
.current_version(&env!("CARGO_PKG_VERSION"))
.current_version(env!("CARGO_PKG_VERSION"))
.build()?;
let current_version = updater.current_version();

View File

@ -2,7 +2,7 @@ dependencies = { }
[package]
name = "leo-linter"
version = "1.5.2"
version = "1.5.3"
authors = [ "The Aleo Team <hello@aleo.org>" ]
description = "Linter of the Leo programming language"
homepage = "https://aleo.org"

View File

@ -1,6 +1,6 @@
[package]
name = "leo-package"
version = "1.5.2"
version = "1.5.3"
authors = [ "The Aleo Team <hello@aleo.org>" ]
description = "Package parser of the Leo programming language"
homepage = "https://aleo.org"

View File

@ -22,8 +22,7 @@ use serde::Deserialize;
use std::{
borrow::Cow,
fs::{
File,
{self},
File, {self},
},
io::Write,
path::Path,

View File

@ -22,8 +22,7 @@ use serde::Deserialize;
use std::{
borrow::Cow,
fs::{
File,
{self},
File, {self},
},
io::Write,
path::Path,

View File

@ -22,8 +22,7 @@ use serde::Deserialize;
use std::{
borrow::Cow,
fs::{
File,
{self},
File, {self},
},
io::Write,
path::Path,

View File

@ -22,8 +22,7 @@ use serde::Deserialize;
use std::{
borrow::Cow,
fs::{
File,
{self},
File, {self},
},
io::Write,
path::Path,

View File

@ -22,8 +22,7 @@ use serde::Deserialize;
use std::{
borrow::Cow,
fs::{
File,
{self},
File, {self},
},
io::Write,
path::Path,

View File

@ -22,8 +22,7 @@ use serde::Deserialize;
use std::{
borrow::Cow,
fs::{
File,
{self},
File, {self},
},
io::Write,
path::Path,

View File

@ -22,8 +22,7 @@ use serde::Deserialize;
use std::{
borrow::Cow,
fs::{
File,
{self},
File, {self},
},
io::Write,
path::Path,

View File

@ -123,14 +123,14 @@ impl Package {
}
// Check if the input file already exists.
let input_file = InputFile::new(&package_name);
let input_file = InputFile::new(package_name);
if input_file.exists_at(path) {
existing_files.push(input_file.filename());
result = false;
}
// Check if the state file already exists.
let state_file = StateFile::new(&package_name);
let state_file = StateFile::new(package_name);
if state_file.exists_at(path) {
existing_files.push(state_file.filename());
result = false;
@ -157,24 +157,24 @@ impl Package {
}
// Check if the manifest file exists.
if !Manifest::exists_at(&path) {
if !Manifest::exists_at(path) {
return false;
}
// Check if the input file exists.
let input_file = InputFile::new(&package_name);
if !input_file.exists_at(&path) {
let input_file = InputFile::new(package_name);
if !input_file.exists_at(path) {
return false;
}
// Check if the state file exists.
let state_file = StateFile::new(&package_name);
if !state_file.exists_at(&path) {
let state_file = StateFile::new(package_name);
if !state_file.exists_at(path) {
return false;
}
// Check if the main file exists.
if !MainFile::exists_at(&path) {
if !MainFile::exists_at(path) {
return false;
}
@ -195,34 +195,34 @@ impl Package {
// Next, initialize this directory as a Leo package.
{
// Create the manifest file.
Manifest::new(&package_name, author)?.write_to(&path)?;
Manifest::new(package_name, author)?.write_to(path)?;
// Verify that the .gitignore file does not exist.
if !Gitignore::exists_at(&path) {
if !Gitignore::exists_at(path) {
// Create the .gitignore file.
Gitignore::new().write_to(&path)?;
Gitignore::new().write_to(path)?;
}
// Verify that the README.md file does not exist.
if !README::exists_at(&path) {
if !README::exists_at(path) {
// Create the README.md file.
README::new(package_name).write_to(&path)?;
README::new(package_name).write_to(path)?;
}
// Create the source directory.
SourceDirectory::create(&path)?;
SourceDirectory::create(path)?;
// Create the input directory.
InputsDirectory::create(&path)?;
InputsDirectory::create(path)?;
// Create the input file in the inputs directory.
InputFile::new(&package_name).write_to(&path)?;
InputFile::new(package_name).write_to(path)?;
// Create the state file in the inputs directory.
StateFile::new(&package_name).write_to(&path)?;
StateFile::new(package_name).write_to(path)?;
// Create the main file in the source directory.
MainFile::new(&package_name).write_to(&path)?;
MainFile::new(package_name).write_to(path)?;
}
// Next, verify that a valid Leo package has been initialized in this directory
{

View File

@ -21,12 +21,8 @@ use crate::{
imports::IMPORTS_DIRECTORY_NAME,
inputs::{INPUTS_DIRECTORY_NAME, INPUT_FILE_EXTENSION, STATE_FILE_EXTENSION},
outputs::{
CHECKSUM_FILE_EXTENSION,
CIRCUIT_FILE_EXTENSION,
OUTPUTS_DIRECTORY_NAME,
PROOF_FILE_EXTENSION,
PROVING_KEY_FILE_EXTENSION,
VERIFICATION_KEY_FILE_EXTENSION,
CHECKSUM_FILE_EXTENSION, CIRCUIT_FILE_EXTENSION, OUTPUTS_DIRECTORY_NAME, PROOF_FILE_EXTENSION,
PROVING_KEY_FILE_EXTENSION, VERIFICATION_KEY_FILE_EXTENSION,
},
root::{MANIFEST_FILENAME, README_FILENAME},
source::{SOURCE_DIRECTORY_NAME, SOURCE_FILE_EXTENSION},
@ -36,8 +32,7 @@ use serde::Deserialize;
use std::{
borrow::Cow,
fs::{
File,
{self},
File, {self},
},
io::{Read, Write},
path::Path,

View File

@ -22,8 +22,7 @@ pub mod manifest;
use lazy_static::lazy_static;
use std::{
cell::RefCell,
env,
fs,
env, fs,
path::PathBuf,
sync::atomic::{AtomicUsize, Ordering},
};

View File

@ -1,6 +1,6 @@
[package]
name = "leo-parser"
version = "1.5.2"
version = "1.5.3"
authors = [ "The Aleo Team <hello@aleo.org>" ]
description = "AST generated by pest from the Leo grammar rules"
homepage = "https://aleo.org"
@ -24,7 +24,7 @@ harness = false
[dependencies.leo-ast]
path = "../ast"
version = "1.5.2"
version = "1.5.3"
[dependencies.lazy_static]
version = "1.3.0"

View File

@ -48,7 +48,7 @@ fn main() -> Result<(), SyntaxError> {
let input_filepath = Path::new(&cli_arguments[1]);
// Construct the serialized syntax tree.
let serialized_leo_tree = to_leo_tree(&input_filepath)?;
let serialized_leo_tree = to_leo_tree(input_filepath)?;
println!("{}", serialized_leo_tree);
// Determine the output directory.

View File

@ -168,7 +168,18 @@ impl ParserContext {
if let Some(SpannedToken { span, .. }) = self.eat(Token::Mul) {
Ok(PackageAccess::Star { span })
} else {
let name = self.expect_ident()?;
let mut name = self.expect_ident()?;
// Allow dashes in the accessed members (should only be used for directories).
// If imported member does not exist, code will fail on ASG level.
if let Token::Minus = self.peek_token().as_ref() {
let span = self.expect(Token::Minus)?;
name.span = name.span + span;
let next = self.expect_ident()?;
name.span = name.span + next.span;
name.name = format_tendril!("{}-{}", name.name, next.name);
}
if self.peek_token().as_ref() == &Token::Dot {
self.backtrack(SpannedToken {
token: Token::Ident(name.name),
@ -222,7 +233,7 @@ impl ParserContext {
base.name = format_tendril!("{}{}", base.name, next.name);
base.span = base.span + next.span;
}
x if KEYWORD_TOKENS.contains(&x) => {
x if KEYWORD_TOKENS.contains(x) => {
let next = self.expect_loose_identifier()?;
base.name = format_tendril!("{}{}", base.name, next.name);
base.span = base.span + next.span;
@ -379,10 +390,13 @@ impl ParserContext {
self.expect(Token::LeftCurly)?;
let members = self.parse_circuit_declaration()?;
Ok((name.clone(), Circuit {
circuit_name: name,
members,
}))
Ok((
name.clone(),
Circuit {
circuit_name: name,
members,
},
))
}
///
@ -459,14 +473,17 @@ impl ParserContext {
None
};
let block = self.parse_block()?;
Ok((name.clone(), Function {
annotations,
identifier: name,
input: inputs,
output,
span: start + block.span.clone(),
block,
}))
Ok((
name.clone(),
Function {
annotations,
identifier: name,
input: inputs,
output,
span: start + block.span.clone(),
block,
},
))
}
///

View File

@ -281,7 +281,7 @@ impl ParserContext {
"log" => ConsoleFunction::Log(self.parse_console_args()?),
x => {
return Err(SyntaxError::unexpected_ident(
&x,
x,
&["assert", "error", "log"],
&function.span,
));

View File

@ -101,7 +101,7 @@ impl Token {
return None;
}
if let Ok(ascii_number) = u8::from_str_radix(&hex_string, 16) {
if let Ok(ascii_number) = u8::from_str_radix(hex_string, 16) {
// According to RFC, we allow only values less than 128.
if ascii_number > 127 {
return None;
@ -123,7 +123,7 @@ impl Token {
return None;
}
if let Ok(hex) = u32::from_str_radix(&unicode_number, 16) {
if let Ok(hex) = u32::from_str_radix(unicode_number, 16) {
if let Some(character) = std::char::from_u32(hex) {
// scalar
return Some(Char::Scalar(character));

View File

@ -82,17 +82,20 @@ pub(crate) fn tokenize(path: &str, input: StrTendril) -> Result<Vec<SpannedToken
if token_len == 0 && index == input.len() {
break;
} else if token_len == 0 {
return Err(TokenError::unexpected_token(&input[index..index + 1], &Span {
line_start: line_no,
line_stop: line_no,
col_start: index - line_start + 1,
col_stop: index - line_start + 2,
path,
content: input.subtendril(
line_start as u32,
input[line_start..].find('\n').unwrap_or_else(|| input.len()) as u32,
),
}));
return Err(TokenError::unexpected_token(
&input[index..index + 1],
&Span {
line_start: line_no,
line_stop: line_no,
col_start: index - line_start + 1,
col_stop: index - line_start + 2,
path,
content: input.subtendril(
line_start as u32,
input[line_start..].find('\n').unwrap_or_else(|| input.len()) as u32,
),
},
));
}
if input.as_bytes()[index] == b'\n' {
line_no += 1;

View File

@ -1,6 +1,6 @@
[package]
name = "leo-state"
version = "1.5.2"
version = "1.5.3"
authors = [ "The Aleo Team <hello@aleo.org>" ]
description = "State parser of the Leo programming language"
homepage = "https://aleo.org"
@ -19,25 +19,25 @@ edition = "2018"
[dependencies.leo-input]
path = "../input"
version = "1.5.2"
version = "1.5.3"
[dependencies.leo-ast]
path = "../ast"
version = "1.5.2"
version = "1.5.3"
[dependencies.snarkvm-algorithms]
version = "0.7.4"
version = "0.7.6"
[dependencies.snarkvm-curves]
version = "0.7.5"
version = "0.7.9"
default-features = false
[dependencies.snarkvm-dpc]
version = "0.7.5"
version = "0.7.9"
features = [ "testnet1" ]
[dependencies.snarkvm-utilities]
version = "0.7.4"
version = "0.7.6"
[dependencies.indexmap]
version = "1.7.0"

Some files were not shown because too many files have changed in this diff Show More