-
Notifications
You must be signed in to change notification settings - Fork 659
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Interpreter. #28441
base: mainnet
Are you sure you want to change the base?
Interpreter. #28441
Conversation
@@ -110,6 +115,7 @@ impl LeoError { | |||
UtilError(error) => error.error_code(), | |||
LastErrorCode(_) => unreachable!(), | |||
Anyhow(_) => "SnarkVM Error".to_string(), // todo: implement error codes for snarkvm errors. | |||
InterpreterHalt(_) => "Interpreter Halt".to_string(), |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Should we give these a proper error code?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'm not sure. My thought is that unlike the other error variants, InterpreterHalt doesn't necessarily represent undesired/unexpected behavior - the user may be stepping through code perfectly well expecting that an assert may trigger (or whatever).
Into, | ||
Over, | ||
Step, | ||
Run, |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
We'll prolly wanna throw in the following commands to manipulate the "global" context.
- Set mapping value
- Get mapping value
- Remove mapping value
- Set block height
- Set caller
- Set signer
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Oh wait, would users just write leo syntax for the mapping ops?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
That's right; the mapping stuff can be done just by writing Leo code at the REPL.
interpreter/src/cursor.rs
Outdated
integers::Integer as SvmIntegerParam, | ||
}; | ||
|
||
type SvmAddress = SvmAddressParam<TestnetV0>; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Do we want these types parameterized over the Network
?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
At the moment the interpreter only works with TestnetV0
. It's not clear to me whether it's important that it works with the other Network
s. What do you think?
interpreter/src/cursor.rs
Outdated
} | ||
|
||
/// Doesn't correspond to Aleo's shl, because it | ||
/// does not fail when set bits are shifted out. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Should we match Aleo's impl?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The interpreter will match Aleo's implementation; just this utility function does not.
interpreter/src/cursor.rs
Outdated
} | ||
|
||
#[derive(Clone, Debug, Default, Eq, PartialEq, Hash)] | ||
pub struct Future(pub Vec<AsyncExecution>); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
That way I've been thinking about Future
s is that they are a single AsyncExecution
, whose arguments
can be other AsyncExecution
s. I'm sure I'll understand as I make it further down, but is there a reason why it's a vec here?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
What I have is that a Future is a sequence of AsyncExecution
s, and when an async function calls await, it collects that Future's AsyncExecution
s into its Future, which it will return when it finishes executing.
It's not clear to me that there is any advantage in having a tree of executions as opposed to just a sequence. Is there?
}; | ||
} | ||
|
||
if let Some(value) = match expression { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Organizational nit. Consider splitting the functional components (expression evaluation) and control flow of the REPL loop for easier maintenance.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Well, I thought I did that. Where do you consider them to be interwoven?
- reorder dependencies - typos - split into different files
This ensures the interpreter never tries to display any of these frames as if they came from a file. Also handle definitions where the left hand side is a tuple of identifiers.
No description provided.