mirror of
https://github.com/ProvableHQ/leo.git
synced 2024-11-25 21:16:41 +03:00
rest of Aleo commands
This commit is contained in:
parent
b2f7fd718b
commit
334881cef5
@ -256,7 +256,7 @@ pub struct Cursor<'a> {
|
||||
|
||||
pub signer: SvmAddress,
|
||||
|
||||
rng: ChaCha20Rng,
|
||||
pub rng: ChaCha20Rng,
|
||||
|
||||
pub block_height: u32,
|
||||
|
||||
@ -322,14 +322,14 @@ impl<'a> Cursor<'a> {
|
||||
self.globals.get(&GlobalId { program: context.program, name }).cloned()
|
||||
}
|
||||
|
||||
fn lookup_mapping(&self, program: Option<Symbol>, name: Symbol) -> Option<&HashMap<Value, Value>> {
|
||||
pub fn lookup_mapping(&self, program: Option<Symbol>, name: Symbol) -> Option<&HashMap<Value, Value>> {
|
||||
let Some(program) = program.or(self.contexts.last().map(|c| c.program)) else {
|
||||
panic!("no program for mapping lookup");
|
||||
};
|
||||
self.mappings.get(&GlobalId { program, name })
|
||||
}
|
||||
|
||||
fn lookup_mapping_mut(&mut self, program: Option<Symbol>, name: Symbol) -> Option<&mut HashMap<Value, Value>> {
|
||||
pub fn lookup_mapping_mut(&mut self, program: Option<Symbol>, name: Symbol) -> Option<&mut HashMap<Value, Value>> {
|
||||
let Some(program) = program.or(self.contexts.last().map(|c| c.program)) else {
|
||||
panic!("no program for mapping lookup");
|
||||
};
|
||||
|
@ -19,14 +19,39 @@ use super::*;
|
||||
use leo_ast::{BinaryOperation, CoreFunction, IntegerType, Type, UnaryOperation};
|
||||
|
||||
use snarkvm::{
|
||||
prelude::{Boolean, Identifier, Literal, LiteralType, PlaintextType, Register, TestnetV0, integers::Integer},
|
||||
prelude::{
|
||||
Boolean,
|
||||
Field,
|
||||
Identifier,
|
||||
Literal,
|
||||
LiteralType,
|
||||
Network as _,
|
||||
PlaintextType,
|
||||
Register,
|
||||
TestnetV0,
|
||||
ToBits as _,
|
||||
ToBytes as _,
|
||||
integers::Integer,
|
||||
},
|
||||
synthesizer::{Command, Instruction},
|
||||
};
|
||||
use snarkvm_synthesizer_program::{CallOperator, CastType, Operand};
|
||||
|
||||
use rand::Rng as _;
|
||||
use rand_chacha::{ChaCha20Rng, rand_core::SeedableRng};
|
||||
use std::mem;
|
||||
|
||||
impl Cursor<'_> {
|
||||
fn mapping_by_call_operator(&self, operator: &CallOperator<TestnetV0>) -> Option<&HashMap<Value, Value>> {
|
||||
let (program, name) = match operator {
|
||||
CallOperator::Locator(locator) => {
|
||||
(Some(snarkvm_identifier_to_symbol(locator.name())), snarkvm_identifier_to_symbol(locator.resource()))
|
||||
}
|
||||
CallOperator::Resource(id) => (None, snarkvm_identifier_to_symbol(id)),
|
||||
};
|
||||
self.lookup_mapping(program, name)
|
||||
}
|
||||
|
||||
fn get_register(&self, reg: Register<TestnetV0>) -> &Value {
|
||||
let Some(Frame { element: Element::AleoExecution { registers, .. }, .. }) = self.frames.last() else {
|
||||
panic!();
|
||||
@ -742,21 +767,108 @@ impl Cursor<'_> {
|
||||
|
||||
fn step_aleo_command(&mut self, command: Command<TestnetV0>) -> Result<()> {
|
||||
use Command::*;
|
||||
match command {
|
||||
Instruction(instruction) => self.step_aleo_instruction(instruction)?,
|
||||
|
||||
let (value, destination) = match command {
|
||||
Instruction(instruction) => {
|
||||
self.step_aleo_instruction(instruction)?;
|
||||
return Ok(());
|
||||
}
|
||||
Await(await_) => {
|
||||
let Value::Future(future) = self.get_register(await_.register().clone()) else {
|
||||
halt_no_span!("attempted to await a non-future");
|
||||
};
|
||||
self.contexts.add_future(future.clone());
|
||||
self.increment_instruction_index();
|
||||
return Ok(());
|
||||
}
|
||||
Contains(contains) => {
|
||||
let mapping = self.mapping_by_call_operator(contains.mapping()).expect("mapping should be present");
|
||||
let key = self.operand_value(contains.key());
|
||||
let result = Value::Bool(mapping.contains_key(&key));
|
||||
self.increment_instruction_index();
|
||||
(result, contains.destination().clone())
|
||||
}
|
||||
Get(get) => {
|
||||
let key = self.operand_value(get.key());
|
||||
let value = self.mapping_by_call_operator(get.mapping()).and_then(|mapping| mapping.get(&key)).cloned();
|
||||
self.increment_instruction_index();
|
||||
|
||||
match value {
|
||||
Some(v) => (v, get.destination().clone()),
|
||||
None => halt_no_span!("map access failure: {key}"),
|
||||
}
|
||||
}
|
||||
GetOrUse(get_or_use) => {
|
||||
let key = self.operand_value(get_or_use.key());
|
||||
let value =
|
||||
self.mapping_by_call_operator(get_or_use.mapping()).and_then(|mapping| mapping.get(&key)).cloned();
|
||||
|
||||
let use_value = value.unwrap_or_else(|| self.operand_value(get_or_use.default()));
|
||||
self.increment_instruction_index();
|
||||
|
||||
(use_value, get_or_use.destination().clone())
|
||||
}
|
||||
Remove(remove) => {
|
||||
let key = self.operand_value(remove.key());
|
||||
let mapping_name = snarkvm_identifier_to_symbol(remove.mapping_name());
|
||||
let maybe_mapping = self.lookup_mapping_mut(None, mapping_name);
|
||||
match maybe_mapping {
|
||||
None => halt_no_span!("no such mapping {mapping_name}"),
|
||||
Some(mapping) => {
|
||||
mapping.remove(&key);
|
||||
}
|
||||
}
|
||||
self.increment_instruction_index();
|
||||
return Ok(());
|
||||
}
|
||||
Set(set) => {
|
||||
let key = self.operand_value(set.key());
|
||||
let value = self.operand_value(set.value());
|
||||
let mapping_name = snarkvm_identifier_to_symbol(set.mapping_name());
|
||||
let maybe_mapping = self.lookup_mapping_mut(None, mapping_name);
|
||||
match maybe_mapping {
|
||||
None => halt_no_span!("no such mapping {mapping_name}"),
|
||||
Some(mapping) => {
|
||||
mapping.insert(key, value);
|
||||
}
|
||||
}
|
||||
self.increment_instruction_index();
|
||||
return Ok(());
|
||||
}
|
||||
RandChaCha(rand) => {
|
||||
// If there are operands, they are additional seeds.
|
||||
let mut bits = Vec::new();
|
||||
for value in rand.operands().iter().map(|op| self.operand_value(op)) {
|
||||
value.write_bits_le(&mut bits);
|
||||
}
|
||||
let field: Field<TestnetV0> = self.rng.gen();
|
||||
field.write_bits_le(&mut bits);
|
||||
let seed_vec = TestnetV0::hash_bhp1024(&bits)?.to_bytes_le()?;
|
||||
let mut seed = [0u8; 32];
|
||||
seed.copy_from_slice(&seed_vec[..32]);
|
||||
let mut rng = ChaCha20Rng::from_seed(seed);
|
||||
let value = match rand.destination_type() {
|
||||
LiteralType::Address => Value::Address(rng.gen()),
|
||||
LiteralType::Boolean => Value::Bool(rng.gen()),
|
||||
LiteralType::Field => Value::Field(rng.gen()),
|
||||
LiteralType::Group => Value::Group(rng.gen()),
|
||||
LiteralType::I8 => Value::I8(rng.gen()),
|
||||
LiteralType::I16 => Value::I16(rng.gen()),
|
||||
LiteralType::I32 => Value::I32(rng.gen()),
|
||||
LiteralType::I64 => Value::I64(rng.gen()),
|
||||
LiteralType::I128 => Value::I128(rng.gen()),
|
||||
LiteralType::U8 => Value::U8(rng.gen()),
|
||||
LiteralType::U16 => Value::U16(rng.gen()),
|
||||
LiteralType::U32 => Value::U32(rng.gen()),
|
||||
LiteralType::U64 => Value::U64(rng.gen()),
|
||||
LiteralType::U128 => Value::U128(rng.gen()),
|
||||
LiteralType::Scalar => Value::Scalar(rng.gen()),
|
||||
LiteralType::Signature => halt_no_span!("Cannot create a random signature"),
|
||||
LiteralType::String => halt_no_span!("Cannot create a random string"),
|
||||
};
|
||||
self.increment_instruction_index();
|
||||
(value, rand.destination().clone())
|
||||
}
|
||||
Contains(_) => todo!(),
|
||||
Get(_) => todo!(),
|
||||
GetOrUse(_) => todo!(),
|
||||
RandChaCha(_) => todo!(),
|
||||
Remove(_) => todo!(),
|
||||
Set(_) => todo!(),
|
||||
BranchEq(branch_eq) => {
|
||||
let first = self.operand_value(branch_eq.first());
|
||||
let second = self.operand_value(branch_eq.second());
|
||||
@ -765,6 +877,7 @@ impl Cursor<'_> {
|
||||
} else {
|
||||
self.increment_instruction_index();
|
||||
}
|
||||
return Ok(());
|
||||
}
|
||||
BranchNeq(branch_neq) => {
|
||||
let first = self.operand_value(branch_neq.first());
|
||||
@ -774,9 +887,13 @@ impl Cursor<'_> {
|
||||
} else {
|
||||
self.increment_instruction_index();
|
||||
}
|
||||
return Ok(());
|
||||
}
|
||||
Position(_) => {}
|
||||
}
|
||||
Position(_) => return Ok(()),
|
||||
};
|
||||
|
||||
self.set_register(destination, value);
|
||||
|
||||
Ok(())
|
||||
}
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user