Remove Increment, Decrement statements from AST

This commit is contained in:
Pranav Gaddamadugu 2023-04-03 09:17:45 -07:00
parent 4ee06d4342
commit 4f27c92f15
10 changed files with 0 additions and 310 deletions

View File

@ -75,10 +75,8 @@ pub trait StatementConsumer {
Statement::Block(stmt) => self.consume_block(stmt),
Statement::Conditional(stmt) => self.consume_conditional(stmt),
Statement::Console(stmt) => self.consume_console(stmt),
Statement::Decrement(stmt) => self.consume_decrement(stmt),
Statement::Definition(stmt) => self.consume_definition(stmt),
Statement::Expression(stmt) => self.consume_expression_statement(stmt),
Statement::Increment(stmt) => self.consume_increment(stmt),
Statement::Iteration(stmt) => self.consume_iteration(*stmt),
Statement::Return(stmt) => self.consume_return(stmt),
}
@ -94,14 +92,10 @@ pub trait StatementConsumer {
fn consume_console(&mut self, input: ConsoleStatement) -> Self::Output;
fn consume_decrement(&mut self, input: DecrementStatement) -> Self::Output;
fn consume_definition(&mut self, input: DefinitionStatement) -> Self::Output;
fn consume_expression_statement(&mut self, input: ExpressionStatement) -> Self::Output;
fn consume_increment(&mut self, input: IncrementStatement) -> Self::Output;
fn consume_iteration(&mut self, input: IterationStatement) -> Self::Output;
fn consume_return(&mut self, input: ReturnStatement) -> Self::Output;

View File

@ -157,10 +157,8 @@ pub trait StatementReconstructor: ExpressionReconstructor {
}
Statement::Conditional(stmt) => self.reconstruct_conditional(stmt),
Statement::Console(stmt) => self.reconstruct_console(stmt),
Statement::Decrement(stmt) => self.reconstruct_decrement(stmt),
Statement::Definition(stmt) => self.reconstruct_definition(stmt),
Statement::Expression(stmt) => self.reconstruct_expression_statement(stmt),
Statement::Increment(stmt) => self.reconstruct_increment(stmt),
Statement::Iteration(stmt) => self.reconstruct_iteration(*stmt),
Statement::Return(stmt) => self.reconstruct_return(stmt),
}
@ -239,19 +237,6 @@ pub trait StatementReconstructor: ExpressionReconstructor {
)
}
// TODO: Reconstructor should visit this.
fn reconstruct_decrement(&mut self, input: DecrementStatement) -> (Statement, Self::AdditionalOutput) {
(
Statement::Decrement(DecrementStatement {
mapping: input.mapping,
amount: input.amount,
index: input.index,
span: input.span,
}),
Default::default(),
)
}
fn reconstruct_definition(&mut self, input: DefinitionStatement) -> (Statement, Self::AdditionalOutput) {
(
Statement::Definition(DefinitionStatement {
@ -275,19 +260,6 @@ pub trait StatementReconstructor: ExpressionReconstructor {
)
}
// TODO: Reconstructor should visit this.
fn reconstruct_increment(&mut self, input: IncrementStatement) -> (Statement, Self::AdditionalOutput) {
(
Statement::Increment(IncrementStatement {
mapping: input.mapping,
index: input.index,
amount: input.amount,
span: input.span,
}),
Default::default(),
)
}
fn reconstruct_iteration(&mut self, input: IterationStatement) -> (Statement, Self::AdditionalOutput) {
(
Statement::Iteration(Box::new(IterationStatement {

View File

@ -122,10 +122,8 @@ pub trait StatementVisitor<'a>: ExpressionVisitor<'a> {
Statement::Block(stmt) => self.visit_block(stmt),
Statement::Conditional(stmt) => self.visit_conditional(stmt),
Statement::Console(stmt) => self.visit_console(stmt),
Statement::Decrement(stmt) => self.visit_decrement(stmt),
Statement::Definition(stmt) => self.visit_definition(stmt),
Statement::Expression(stmt) => self.visit_expression_statement(stmt),
Statement::Increment(stmt) => self.visit_increment(stmt),
Statement::Iteration(stmt) => self.visit_iteration(stmt),
Statement::Return(stmt) => self.visit_return(stmt),
}
@ -173,12 +171,6 @@ pub trait StatementVisitor<'a>: ExpressionVisitor<'a> {
};
}
fn visit_decrement(&mut self, input: &'a DecrementStatement) {
self.visit_expression(&input.amount, &Default::default());
self.visit_expression(&input.index, &Default::default());
self.visit_identifier(&input.mapping, &Default::default());
}
fn visit_definition(&mut self, input: &'a DefinitionStatement) {
self.visit_expression(&input.value, &Default::default());
}
@ -187,12 +179,6 @@ pub trait StatementVisitor<'a>: ExpressionVisitor<'a> {
self.visit_expression(&input.expression, &Default::default());
}
fn visit_increment(&mut self, input: &'a IncrementStatement) {
self.visit_expression(&input.amount, &Default::default());
self.visit_expression(&input.index, &Default::default());
self.visit_identifier(&input.mapping, &Default::default());
}
fn visit_iteration(&mut self, input: &'a IterationStatement) {
self.visit_expression(&input.start, &Default::default());
self.visit_expression(&input.stop, &Default::default());

View File

@ -1,43 +0,0 @@
// Copyright (C) 2019-2023 Aleo Systems Inc.
// This file is part of the Leo library.
// The Leo library is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
// The Leo library is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.
// You should have received a copy of the GNU General Public License
// along with the Leo library. If not, see <https://www.gnu.org/licenses/>.
use crate::{Expression, Identifier, Node};
use leo_span::Span;
use core::fmt;
use serde::{Deserialize, Serialize};
/// A decrement statement `decrement(foo, bar, 1);`.
#[derive(Clone, PartialEq, Eq, Serialize, Deserialize, Debug)]
pub struct DecrementStatement {
/// The mapping to be modified.
pub mapping: Identifier,
/// The index of the element to be decremented.
pub index: Expression,
/// The amount to decrement the element by.
pub amount: Expression,
/// The span of `decrement(foo, bar, 1)` excluding the semicolon.
pub span: Span,
}
impl fmt::Display for DecrementStatement {
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
write!(f, "decrement({}, {}, {});", self.mapping, self.index, self.amount)
}
}
crate::simple_node_impl!(DecrementStatement);

View File

@ -1,43 +0,0 @@
// Copyright (C) 2019-2023 Aleo Systems Inc.
// This file is part of the Leo library.
// The Leo library is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
// The Leo library is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.
// You should have received a copy of the GNU General Public License
// along with the Leo library. If not, see <https://www.gnu.org/licenses/>.
use crate::{Expression, Identifier, Node};
use leo_span::Span;
use core::fmt;
use serde::{Deserialize, Serialize};
/// An increment statement `increment(foo, bar, 1);`.
#[derive(Clone, PartialEq, Eq, Serialize, Deserialize, Debug)]
pub struct IncrementStatement {
/// The mapping to be modified.
pub mapping: Identifier,
/// The index of the element to be incremented.
pub index: Expression,
/// The amount to increment the element by.
pub amount: Expression,
/// The span of `increment(foo, bar, 1)` excluding the semicolon.
pub span: Span,
}
impl fmt::Display for IncrementStatement {
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
write!(f, "increment({}, {}, {});", self.mapping, self.index, self.amount)
}
}
crate::simple_node_impl!(IncrementStatement);

View File

@ -29,18 +29,12 @@ pub use conditional::*;
pub mod console;
pub use console::*;
pub mod decrement;
pub use decrement::*;
pub mod definition;
pub use definition::*;
pub mod expression;
pub use expression::*;
pub mod increment;
pub use increment::*;
pub mod iteration;
pub use iteration::*;
@ -67,14 +61,10 @@ pub enum Statement {
Conditional(ConditionalStatement),
/// A console logging statement.
Console(ConsoleStatement),
/// A decrement statement.
Decrement(DecrementStatement),
/// A binding or set of bindings / variables to declare.
Definition(DefinitionStatement),
/// An expression statement
Expression(ExpressionStatement),
/// An increment statement.
Increment(IncrementStatement),
/// A `for` statement.
Iteration(Box<IterationStatement>),
/// A return statement `return expr;`.
@ -96,10 +86,8 @@ impl fmt::Display for Statement {
Statement::Block(x) => x.fmt(f),
Statement::Conditional(x) => x.fmt(f),
Statement::Console(x) => x.fmt(f),
Statement::Decrement(x) => x.fmt(f),
Statement::Definition(x) => x.fmt(f),
Statement::Expression(x) => x.fmt(f),
Statement::Increment(x) => x.fmt(f),
Statement::Iteration(x) => x.fmt(f),
Statement::Return(x) => x.fmt(f),
}
@ -115,10 +103,8 @@ impl Node for Statement {
Block(n) => n.span(),
Conditional(n) => n.span(),
Console(n) => n.span(),
Decrement(n) => n.span(),
Definition(n) => n.span(),
Expression(n) => n.span(),
Increment(n) => n.span(),
Iteration(n) => n.span(),
Return(n) => n.span(),
}
@ -132,10 +118,8 @@ impl Node for Statement {
Block(n) => n.set_span(span),
Conditional(n) => n.set_span(span),
Console(n) => n.set_span(span),
Decrement(n) => n.set_span(span),
Definition(n) => n.set_span(span),
Expression(n) => n.set_span(span),
Increment(n) => n.set_span(span),
Iteration(n) => n.set_span(span),
Return(n) => n.set_span(span),
}

View File

@ -23,11 +23,9 @@ use leo_ast::{
Block,
ConditionalStatement,
ConsoleStatement,
DecrementStatement,
DefinitionStatement,
Expression,
ExpressionStatement,
IncrementStatement,
IterationStatement,
Mode,
Output,
@ -46,10 +44,8 @@ impl<'a> CodeGenerator<'a> {
Statement::Block(stmt) => self.visit_block(stmt),
Statement::Conditional(stmt) => self.visit_conditional(stmt),
Statement::Console(stmt) => self.visit_console(stmt),
Statement::Decrement(stmt) => self.visit_decrement(stmt),
Statement::Definition(stmt) => self.visit_definition(stmt),
Statement::Expression(stmt) => self.visit_expression_statement(stmt),
Statement::Increment(stmt) => self.visit_increment(stmt),
Statement::Iteration(stmt) => self.visit_iteration(stmt),
Statement::Return(stmt) => self.visit_return(stmt),
}
@ -170,24 +166,6 @@ impl<'a> CodeGenerator<'a> {
self.visit_expression(&input.expression).1
}
fn visit_increment(&mut self, input: &'a IncrementStatement) -> String {
let (index, mut instructions) = self.visit_expression(&input.index);
let (amount, amount_instructions) = self.visit_expression(&input.amount);
instructions.push_str(&amount_instructions);
instructions.push_str(&format!(" increment {}[{index}] by {amount};\n", input.mapping));
instructions
}
fn visit_decrement(&mut self, input: &'a DecrementStatement) -> String {
let (index, mut instructions) = self.visit_expression(&input.index);
let (amount, amount_instructions) = self.visit_expression(&input.amount);
instructions.push_str(&amount_instructions);
instructions.push_str(&format!(" decrement {}[{index}] by {amount};\n", input.mapping));
instructions
}
fn visit_assign(&mut self, input: &'a AssignStatement) -> String {
match (&input.place, &input.value) {
(Expression::Identifier(identifier), _) => {

View File

@ -23,12 +23,10 @@ use leo_ast::{
Block,
ConditionalStatement,
ConsoleStatement,
DecrementStatement,
DefinitionStatement,
Expression,
ExpressionReconstructor,
ExpressionStatement,
IncrementStatement,
IterationStatement,
ReturnStatement,
Statement,
@ -125,24 +123,6 @@ impl StatementReconstructor for DeadCodeEliminator {
unreachable!("`ConsoleStatement`s should not be in the AST at this phase of compilation.")
}
fn reconstruct_decrement(&mut self, input: DecrementStatement) -> (Statement, Self::AdditionalOutput) {
// Set the `is_necessary` flag.
self.is_necessary = true;
// Visit the statement.
let statement = Statement::Decrement(DecrementStatement {
mapping: input.mapping,
index: self.reconstruct_expression(input.index).0,
amount: self.reconstruct_expression(input.amount).0,
span: input.span,
});
// Unset the `is_necessary` flag.
self.is_necessary = false;
(statement, Default::default())
}
/// Static single assignment replaces definition statements with assignment statements.
fn reconstruct_definition(&mut self, _: DefinitionStatement) -> (Statement, Self::AdditionalOutput) {
unreachable!("`DefinitionStatement`s should not exist in the AST at this phase of compilation.")
@ -174,24 +154,6 @@ impl StatementReconstructor for DeadCodeEliminator {
}
}
fn reconstruct_increment(&mut self, input: IncrementStatement) -> (Statement, Self::AdditionalOutput) {
// Set the `is_necessary` flag.
self.is_necessary = true;
// Visit the statement.
let statement = Statement::Increment(IncrementStatement {
mapping: input.mapping,
index: self.reconstruct_expression(input.index).0,
amount: self.reconstruct_expression(input.amount).0,
span: input.span,
});
// Unset the `is_necessary` flag.
self.is_necessary = false;
(statement, Default::default())
}
/// Loop unrolling unrolls and removes iteration statements from the program.
fn reconstruct_iteration(&mut self, _: IterationStatement) -> (Statement, Self::AdditionalOutput) {
unreachable!("`IterationStatement`s should not be in the AST at this phase of compilation.");

View File

@ -24,13 +24,11 @@ use leo_ast::{
CallExpression,
ConditionalStatement,
ConsoleStatement,
DecrementStatement,
DefinitionStatement,
Expression,
ExpressionConsumer,
ExpressionStatement,
Identifier,
IncrementStatement,
IterationStatement,
ReturnStatement,
Statement,
@ -200,25 +198,6 @@ impl StatementConsumer for StaticSingleAssigner<'_> {
unreachable!("Parsing guarantees that console statements are not present in the program.")
}
/// Consumes the expressions associated with the `DecrementStatement`, returning the simplified `DecrementStatement`.
fn consume_decrement(&mut self, input: DecrementStatement) -> Self::Output {
// First consume the expression associated with the amount.
let (amount, mut statements) = self.consume_expression(input.amount);
// Then, consume the expression associated with the index.
let (index, index_statements) = self.consume_expression(input.index);
statements.extend(index_statements);
statements.push(Statement::Decrement(DecrementStatement {
mapping: input.mapping,
index,
amount,
span: input.span,
}));
statements
}
/// Consumes the `DefinitionStatement` into an `AssignStatement`, renaming the left-hand-side as appropriate.
fn consume_definition(&mut self, definition: DefinitionStatement) -> Self::Output {
// First consume the right-hand-side of the definition.
@ -299,25 +278,6 @@ impl StatementConsumer for StaticSingleAssigner<'_> {
statements
}
/// Consumes the expressions associated with the `IncrementStatement`, returning a simplified `IncrementStatement`.
fn consume_increment(&mut self, input: IncrementStatement) -> Self::Output {
// First consume the expression associated with the amount.
let (amount, mut statements) = self.consume_expression(input.amount);
// Then, consume the expression associated with the index.
let (index, index_statements) = self.consume_expression(input.index);
statements.extend(index_statements);
statements.push(Statement::Increment(IncrementStatement {
mapping: input.mapping,
index,
amount,
span: input.span,
}));
statements
}
// TODO: Error message
fn consume_iteration(&mut self, _input: IterationStatement) -> Self::Output {
unreachable!("`IterationStatement`s should not be in the AST at this phase of compilation.");

View File

@ -35,10 +35,8 @@ impl<'a> StatementVisitor<'a> for TypeChecker<'a> {
Statement::Block(stmt) => self.visit_block(stmt),
Statement::Conditional(stmt) => self.visit_conditional(stmt),
Statement::Console(stmt) => self.visit_console(stmt),
Statement::Decrement(stmt) => self.visit_decrement(stmt),
Statement::Definition(stmt) => self.visit_definition(stmt),
Statement::Expression(stmt) => self.visit_expression_statement(stmt),
Statement::Increment(stmt) => self.visit_increment(stmt),
Statement::Iteration(stmt) => self.visit_iteration(stmt),
Statement::Return(stmt) => self.visit_return(stmt),
}
@ -152,35 +150,6 @@ impl<'a> StatementVisitor<'a> for TypeChecker<'a> {
unreachable!("Parsing guarantees that console statements are not present in the AST.");
}
fn visit_decrement(&mut self, input: &'a DecrementStatement) {
if !self.is_finalize {
self.emit_err(TypeCheckerError::invalid_operation_outside_finalize("decrement", input.span()));
}
// Assert that the first operand is a mapping.
let mapping_type = self.visit_identifier(&input.mapping, &None);
self.assert_mapping_type(&mapping_type, input.span());
match mapping_type {
None => self.emit_err(TypeCheckerError::could_not_determine_type(input.mapping, input.mapping.span)),
Some(Type::Mapping(mapping_type)) => {
// Check that the index matches the key type of the mapping.
let index_type = self.visit_expression(&input.index, &None);
self.assert_type(&index_type, &mapping_type.key, input.index.span());
// Check that the amount matches the value type of the mapping.
let amount_type = self.visit_expression(&input.amount, &None);
self.assert_type(&amount_type, &mapping_type.value, input.amount.span());
// Check that the amount type is incrementable.
self.assert_field_group_scalar_int_type(&amount_type, input.amount.span());
}
Some(mapping_type) => {
self.emit_err(TypeCheckerError::expected_one_type_of("mapping", mapping_type, input.mapping.span))
}
}
}
fn visit_definition(&mut self, input: &'a DefinitionStatement) {
let declaration =
if input.declaration_type == DeclarationType::Const { VariableType::Const } else { VariableType::Mut };
@ -260,35 +229,6 @@ impl<'a> StatementVisitor<'a> for TypeChecker<'a> {
}
}
fn visit_increment(&mut self, input: &'a IncrementStatement) {
if !self.is_finalize {
self.emit_err(TypeCheckerError::invalid_operation_outside_finalize("increment", input.span()));
}
// Assert that the first operand is a mapping.
let mapping_type = self.visit_identifier(&input.mapping, &None);
self.assert_mapping_type(&mapping_type, input.span());
match mapping_type {
None => self.emit_err(TypeCheckerError::could_not_determine_type(input.mapping, input.mapping.span)),
Some(Type::Mapping(mapping_type)) => {
// Check that the index matches the key type of the mapping.
let index_type = self.visit_expression(&input.index, &None);
self.assert_type(&index_type, &mapping_type.key, input.index.span());
// Check that the amount matches the value type of the mapping.
let amount_type = self.visit_expression(&input.amount, &None);
self.assert_type(&amount_type, &mapping_type.value, input.amount.span());
// Check that the amount type is incrementable.
self.assert_field_group_scalar_int_type(&amount_type, input.amount.span());
}
Some(mapping_type) => {
self.emit_err(TypeCheckerError::expected_one_type_of("mapping", mapping_type, input.mapping.span))
}
}
}
fn visit_iteration(&mut self, input: &'a IterationStatement) {
let iter_type = &Some(input.type_.clone());
self.assert_int_type(iter_type, input.variable.span);