diff --git a/src/ast/mod.rs b/src/ast/mod.rs index 8e79ecd..fcf8590 100644 --- a/src/ast/mod.rs +++ b/src/ast/mod.rs @@ -1,6 +1,36 @@ pub mod node { include!(concat!(env!("OUT_DIR"), "/src/ast/node.rs")); + impl OperatorInner { + pub fn name(&self) -> &'static str { + match self { + OperatorInner::Or => "op_or", + OperatorInner::And => "op_and", + OperatorInner::EqualTo => "op_eq", + OperatorInner::NotEqualTo => "op_neq", + OperatorInner::Greater => "op_gt", + OperatorInner::Less => "op_lt", + OperatorInner::GreaterEqual => "op_ge", + OperatorInner::LessEqual => "op_le", + OperatorInner::Add => "op_add", + OperatorInner::Subtract => "op_sub", + OperatorInner::Multiply => "op_mul", + OperatorInner::Divide => "op_div", + OperatorInner::Modulo => "op_mod", + OperatorInner::LeftShift => "op_ls", + OperatorInner::RightShift => "op_rs", + OperatorInner::Spread => "op_spread", + OperatorInner::Star => "op_star", + OperatorInner::Not => "op_not", + OperatorInner::Negative => "op_neg", + OperatorInner::PlusPlus => "op_pp", + OperatorInner::MinusMinus => "op_mm", + OperatorInner::CallOp => "op_call", + OperatorInner::Index => "op_index", + } + } + } + impl Default for Parameters { fn default() -> Self { Self::new(vec![]) diff --git a/src/name_analysis/gather.rs b/src/name_analysis/gather.rs index 3a2d75b..14577bf 100644 --- a/src/name_analysis/gather.rs +++ b/src/name_analysis/gather.rs @@ -1,10 +1,13 @@ use crate::ast::ast_node::{AstNode, AstNodeRef}; use crate::ast::node::{ - Class, CompilationUnit, Function, FunctionBlockBody, FunctionBody, Identifier, Interface, - Module, Namespace, Statement, UseStatement, UseStatementSuffix, VariableDeclaration, + Class, CompilationUnit, Function, FunctionBody, Identifier, Interface, + InterfaceDefaultFunction, InterfaceDefaultOperatorFunction, InterfaceFunction, + InterfaceOperatorFunction, Member, Module, Namespace, OperatorFunction, PlatformFunction, + PlatformOperatorFunction, Statement, UseStatement, UseStatementSuffix, VariableDeclaration, }; use crate::diagnostic::DmDiagnostic; use crate::name_analysis::fqn_context::FqnContext; +use crate::name_analysis::symbol::class_member_symbol::ClassMemberSymbol; use crate::name_analysis::symbol::function_symbol::FunctionSymbol; use crate::name_analysis::symbol::module_symbol::ModuleSymbol; use crate::name_analysis::symbol::source_definition::SourceDefinition; @@ -67,9 +70,14 @@ fn gather_node( diagnostics: &mut Vec, ) { match node { - AstNodeRef::Operator(_) => {} + AstNodeRef::Operator(_) => { + unreachable!(); + } + AstNodeRef::OperatorInner(_) => { + unreachable!(); + } AstNodeRef::Identifier(_) => { - unreachable!() + unreachable!(); } AstNodeRef::FullyQualifiedName(_) => {} AstNodeRef::TypeUseList(_) => {} @@ -98,13 +106,13 @@ fn gather_node( gather_use_statement(use_statement, symbol_table, diagnostics); } AstNodeRef::UseStatementPrefix(_) => { - unreachable!() + unreachable!(); } AstNodeRef::UseStatementSuffix(_) => { - unreachable!() + unreachable!(); } AstNodeRef::UseList(_) => { - unreachable!() + unreachable!(); } AstNodeRef::ModuleLevelDeclaration(module_level_declaration) => { gather_node_children( @@ -142,45 +150,65 @@ fn gather_node( AstNodeRef::Function(function) => { gather_function(function, symbol_table, fqn_context, diagnostics); } - AstNodeRef::OperatorFunction(_) => {} - AstNodeRef::PlatformFunction(_) => {} - AstNodeRef::InterfaceFunction(_) => {} - AstNodeRef::InterfaceDefaultFunction(_) => {} - AstNodeRef::InterfaceOperatorFunction(_) => {} - AstNodeRef::InterfaceDefaultOperatorFunction(_) => {} - AstNodeRef::FunctionBody(function_body) => match function_body { - FunctionBody::FunctionAliasBody(alias_body) => { - gather_node( - alias_body.as_node_ref(), - symbol_table, - fqn_context, - diagnostics, - ); - } - FunctionBody::FunctionEqualsBody(equals_body) => { - gather_node( - equals_body.as_node_ref(), - symbol_table, - fqn_context, - diagnostics, - ); - } - FunctionBody::FunctionBlockBody(block_body) => { - gather_node( - block_body.as_node_ref(), - symbol_table, - fqn_context, - diagnostics, - ); - } - }, - AstNodeRef::FunctionEqualsBody(_) => {} - AstNodeRef::FunctionAliasBody(_) => {} - AstNodeRef::FunctionBlockBody(block_body) => { - gather_function_block_body(block_body, symbol_table, fqn_context, diagnostics); + AstNodeRef::OperatorFunction(operator_function) => { + gather_operator_function(operator_function, symbol_table, fqn_context, diagnostics); + } + AstNodeRef::PlatformFunction(platform_function) => { + gather_platform_function(platform_function, symbol_table, fqn_context, diagnostics); + } + AstNodeRef::PlatformOperatorFunction(platform_operator_function) => { + gather_platform_operator_function( + platform_operator_function, + symbol_table, + fqn_context, + diagnostics, + ); + } + AstNodeRef::InterfaceFunction(interface_function) => { + gather_interface_function(interface_function, symbol_table, fqn_context, diagnostics); + } + AstNodeRef::InterfaceDefaultFunction(interface_default_function) => { + gather_interface_default_function( + interface_default_function, + symbol_table, + fqn_context, + diagnostics, + ); + } + AstNodeRef::InterfaceOperatorFunction(interface_operator_function) => { + gather_interface_operator_function( + interface_operator_function, + symbol_table, + fqn_context, + diagnostics, + ); + } + AstNodeRef::InterfaceDefaultOperatorFunction(interface_default_operator_function) => { + gather_interface_default_operator_function( + interface_default_operator_function, + symbol_table, + fqn_context, + diagnostics, + ); + } + AstNodeRef::FunctionBody(function_body) => { + gather_function_body(function_body, symbol_table, fqn_context, diagnostics); + } + AstNodeRef::FunctionEqualsBody(function_equals_body) => { + gather_node_children(function_equals_body, symbol_table, fqn_context, diagnostics); + } + AstNodeRef::FunctionAliasBody(_) => { + // no-op + } + AstNodeRef::FunctionBlockBody(function_block_body) => { + gather_node_children(function_block_body, symbol_table, fqn_context, diagnostics); + } + AstNodeRef::ClassConstructor(class_constructor) => { + gather_node_children(class_constructor, symbol_table, fqn_context, diagnostics); + } + AstNodeRef::Member(member) => { + gather_member(member, symbol_table, fqn_context, diagnostics); } - AstNodeRef::ClassConstructor(_) => {} - AstNodeRef::Member(_) => {} AstNodeRef::Statement(statement) => match statement { Statement::VariableDeclaration(variable_declaration) => { gather_node( @@ -190,14 +218,59 @@ fn gather_node( diagnostics, ); } - Statement::AssignmentStatement(_) => {} - Statement::ExpressionStatement(_) => {} - Statement::UseStatement(_) => {} - Statement::IfStatement(_) => {} - Statement::WhileStatement(_) => {} - Statement::ForStatement(_) => {} + Statement::AssignmentStatement(assignment_statement) => { + gather_node( + assignment_statement.as_node_ref(), + symbol_table, + fqn_context, + diagnostics, + ); + } + Statement::ExpressionStatement(expression_statement) => { + gather_node( + expression_statement.as_node_ref(), + symbol_table, + fqn_context, + diagnostics, + ); + } + Statement::UseStatement(use_statement) => { + gather_node( + use_statement.as_node_ref(), + symbol_table, + fqn_context, + diagnostics, + ); + } + Statement::IfStatement(if_statement) => gather_node( + if_statement.as_node_ref(), + symbol_table, + fqn_context, + diagnostics, + ), + Statement::WhileStatement(while_statement) => gather_node( + while_statement.as_node_ref(), + symbol_table, + fqn_context, + diagnostics, + ), + Statement::ForStatement(for_statement) => { + gather_node( + for_statement.as_node_ref(), + symbol_table, + fqn_context, + diagnostics, + ); + } }, - AstNodeRef::VariableDeclaration(_) => {} + AstNodeRef::VariableDeclaration(variable_declaration) => { + gather_variable_declaration( + variable_declaration, + symbol_table, + fqn_context, + diagnostics, + ); + } AstNodeRef::AssignmentStatement(_) => {} AstNodeRef::ExpressionStatement(_) => {} AstNodeRef::IfStatement(_) => {} @@ -443,6 +516,12 @@ fn gather_class( fqn_context.push(class.identifier().name()); symbol_table.push_scope(&format!("ClassScope {}", class.identifier().name())); + gather_node( + class.class_constructor().as_node_ref(), + symbol_table, + fqn_context, + diagnostics, + ); for declaration in class.class_level_declarations() { gather_node( declaration.as_node_ref(), @@ -479,25 +558,488 @@ fn gather_function( diagnostics, ); } + symbol_table.push_scope(&format!("FunctionScope {}", function.identifier().name())); + gather_node( + function.generics().as_node_ref(), + symbol_table, + fqn_context, + diagnostics, + ); + gather_node( + function.parameters().as_node_ref(), + symbol_table, + fqn_context, + diagnostics, + ); + gather_node( + function.return_type().as_node_ref(), + symbol_table, + fqn_context, + diagnostics, + ); gather_node( function.function_body().as_node_ref(), symbol_table, fqn_context, diagnostics, ); + symbol_table.pop_scope(); } -fn gather_function_block_body( - function_block_body: &FunctionBlockBody, +fn gather_operator_function( + operator_function: &OperatorFunction, symbol_table: &mut SymbolTable, fqn_context: &mut FqnContext, diagnostics: &mut Vec, ) { - symbol_table.push_scope("FunctionBlockBody"); - gather_node_children(function_block_body, symbol_table, fqn_context, diagnostics); + let function_symbol = FunctionSymbol::without_parameters_or_return_type( + &fqn_context.resolve(&operator_function.operator().inner().name()), + operator_function.operator().inner().name(), + operator_function.is_public(), + false, + Some(SourceDefinition::from_operator( + operator_function.operator(), + )), + ); + if let Err(insert_error) = symbol_table.insert_function_symbol(function_symbol) { + handle_insert_error( + insert_error, + operator_function.operator().inner().name(), + operator_function.operator().file_id(), + operator_function.operator().range(), + "Operator", + diagnostics, + ); + } + symbol_table.push_scope(&format!( + "FunctionScope {}", + operator_function.operator().inner().name() + )); + gather_node( + operator_function.generics().as_node_ref(), + symbol_table, + fqn_context, + diagnostics, + ); + gather_node( + operator_function.parameters().as_node_ref(), + symbol_table, + fqn_context, + diagnostics, + ); + gather_node( + operator_function.return_type().as_node_ref(), + symbol_table, + fqn_context, + diagnostics, + ); + gather_node( + operator_function.function_body().as_node_ref(), + symbol_table, + fqn_context, + diagnostics, + ); symbol_table.pop_scope(); } +fn gather_platform_function( + platform_function: &PlatformFunction, + symbol_table: &mut SymbolTable, + fqn_context: &mut FqnContext, + diagnostics: &mut Vec, +) { + let function_symbol = FunctionSymbol::without_parameters_or_return_type( + &fqn_context.resolve(platform_function.identifier().name()), + platform_function.identifier().name(), + platform_function.is_public(), + true, + Some(SourceDefinition::from_identifier( + platform_function.identifier(), + )), + ); + if let Err(insert_error) = symbol_table.insert_function_symbol(function_symbol) { + handle_insert_error( + insert_error, + platform_function.identifier().name(), + platform_function.identifier().file_id(), + platform_function.identifier().range(), + "Function", + diagnostics, + ); + } + symbol_table.push_scope(&format!( + "PlatformFunctionScope {}", + platform_function.identifier().name() + )); + gather_node( + platform_function.generics().as_node_ref(), + symbol_table, + fqn_context, + diagnostics, + ); + gather_node( + platform_function.parameters().as_node_ref(), + symbol_table, + fqn_context, + diagnostics, + ); + gather_node( + platform_function.return_type().as_node_ref(), + symbol_table, + fqn_context, + diagnostics, + ); + symbol_table.pop_scope(); +} + +fn gather_platform_operator_function( + platform_operator_function: &PlatformOperatorFunction, + symbol_table: &mut SymbolTable, + fqn_context: &mut FqnContext, + diagnostics: &mut Vec, +) { + let function_symbol = FunctionSymbol::without_parameters_or_return_type( + &fqn_context.resolve(platform_operator_function.operator().inner().name()), + platform_operator_function.operator().inner().name(), + platform_operator_function.is_public(), + true, + Some(SourceDefinition::from_operator( + platform_operator_function.operator(), + )), + ); + if let Err(insert_error) = symbol_table.insert_function_symbol(function_symbol) { + handle_insert_error( + insert_error, + platform_operator_function.operator().inner().name(), + platform_operator_function.operator().file_id(), + platform_operator_function.operator().range(), + "Function", + diagnostics, + ); + } + symbol_table.push_scope(&format!( + "PlatformOperatorFunctionScope {}", + platform_operator_function.operator().inner().name() + )); + gather_node( + platform_operator_function.generics().as_node_ref(), + symbol_table, + fqn_context, + diagnostics, + ); + gather_node( + platform_operator_function.parameters().as_node_ref(), + symbol_table, + fqn_context, + diagnostics, + ); + gather_node( + platform_operator_function.return_type().as_node_ref(), + symbol_table, + fqn_context, + diagnostics, + ); + symbol_table.pop_scope(); +} + +fn gather_interface_function( + interface_function: &InterfaceFunction, + symbol_table: &mut SymbolTable, + fqn_context: &mut FqnContext, + diagnostics: &mut Vec, +) { + let function_symbol = FunctionSymbol::without_parameters_or_return_type( + &fqn_context.resolve(interface_function.identifier().name()), + interface_function.identifier().name(), + true, + false, + Some(SourceDefinition::from_identifier( + interface_function.identifier(), + )), + ); + if let Err(insert_error) = symbol_table.insert_function_symbol(function_symbol) { + handle_insert_error( + insert_error, + interface_function.identifier().name(), + interface_function.identifier().file_id(), + interface_function.identifier().range(), + "Type", + diagnostics, + ); + } + symbol_table.push_scope(&format!( + "InterfaceFunctionScope {}", + interface_function.identifier().name() + )); + gather_node( + interface_function.generics().as_node_ref(), + symbol_table, + fqn_context, + diagnostics, + ); + gather_node( + interface_function.parameters().as_node_ref(), + symbol_table, + fqn_context, + diagnostics, + ); + gather_node( + interface_function.return_type().as_node_ref(), + symbol_table, + fqn_context, + diagnostics, + ); + symbol_table.pop_scope(); +} + +fn gather_interface_default_function( + interface_default_function: &InterfaceDefaultFunction, + symbol_table: &mut SymbolTable, + fqn_context: &mut FqnContext, + diagnostics: &mut Vec, +) { + let function_symbol = FunctionSymbol::without_parameters_or_return_type( + &fqn_context.resolve(interface_default_function.identifier().name()), + interface_default_function.identifier().name(), + true, + false, + Some(SourceDefinition::from_identifier( + interface_default_function.identifier(), + )), + ); + if let Err(insert_error) = symbol_table.insert_function_symbol(function_symbol) { + handle_insert_error( + insert_error, + interface_default_function.identifier().name(), + interface_default_function.identifier().file_id(), + interface_default_function.identifier().range(), + "Function", + diagnostics, + ); + } + symbol_table.push_scope(&format!( + "InterfaceDefaultFunctionScope {}", + interface_default_function.identifier().name() + )); + gather_node( + interface_default_function.generics().as_node_ref(), + symbol_table, + fqn_context, + diagnostics, + ); + gather_node( + interface_default_function.parameters().as_node_ref(), + symbol_table, + fqn_context, + diagnostics, + ); + gather_node( + interface_default_function.return_type().as_node_ref(), + symbol_table, + fqn_context, + diagnostics, + ); + gather_node( + interface_default_function.function_body().as_node_ref(), + symbol_table, + fqn_context, + diagnostics, + ); + symbol_table.pop_scope(); +} + +fn gather_interface_operator_function( + interface_operator_function: &InterfaceOperatorFunction, + symbol_table: &mut SymbolTable, + fqn_context: &mut FqnContext, + diagnostics: &mut Vec, +) { + let function_symbol = FunctionSymbol::without_parameters_or_return_type( + &fqn_context.resolve(interface_operator_function.operator().inner().name()), + interface_operator_function.operator().inner().name(), + true, + false, + Some(SourceDefinition::from_operator( + interface_operator_function.operator(), + )), + ); + if let Err(insert_error) = symbol_table.insert_function_symbol(function_symbol) { + handle_insert_error( + insert_error, + interface_operator_function.operator().inner().name(), + interface_operator_function.operator().file_id(), + interface_operator_function.operator().range(), + "Function", + diagnostics, + ); + } + symbol_table.push_scope(&format!( + "InterfaceOperatorFunctionScope {}", + interface_operator_function.operator().inner().name() + )); + gather_node( + interface_operator_function.generics().as_node_ref(), + symbol_table, + fqn_context, + diagnostics, + ); + gather_node( + interface_operator_function.parameters().as_node_ref(), + symbol_table, + fqn_context, + diagnostics, + ); + gather_node( + interface_operator_function.return_type().as_node_ref(), + symbol_table, + fqn_context, + diagnostics, + ); + symbol_table.pop_scope(); +} + +fn gather_interface_default_operator_function( + interface_default_operator_function: &InterfaceDefaultOperatorFunction, + symbol_table: &mut SymbolTable, + fqn_context: &mut FqnContext, + diagnostics: &mut Vec, +) { + let function_symbol = FunctionSymbol::without_parameters_or_return_type( + &fqn_context.resolve( + interface_default_operator_function + .operator() + .inner() + .name(), + ), + interface_default_operator_function + .operator() + .inner() + .name(), + true, + false, + Some(SourceDefinition::from_operator( + interface_default_operator_function.operator(), + )), + ); + if let Err(insert_error) = symbol_table.insert_function_symbol(function_symbol) { + handle_insert_error( + insert_error, + interface_default_operator_function + .operator() + .inner() + .name(), + interface_default_operator_function.operator().file_id(), + interface_default_operator_function.operator().range(), + "Function", + diagnostics, + ); + } + symbol_table.push_scope(&format!( + "InterfaceDefaultOperatorFunctionScope {}", + interface_default_operator_function + .operator() + .inner() + .name() + )); + gather_node( + interface_default_operator_function.generics().as_node_ref(), + symbol_table, + fqn_context, + diagnostics, + ); + gather_node( + interface_default_operator_function + .parameters() + .as_node_ref(), + symbol_table, + fqn_context, + diagnostics, + ); + gather_node( + interface_default_operator_function + .return_type() + .as_node_ref(), + symbol_table, + fqn_context, + diagnostics, + ); + gather_node( + interface_default_operator_function + .function_body() + .as_node_ref(), + symbol_table, + fqn_context, + diagnostics, + ); + symbol_table.pop_scope(); +} + +fn gather_function_body( + function_body: &FunctionBody, + symbol_table: &mut SymbolTable, + fqn_context: &mut FqnContext, + diagnostics: &mut Vec, +) { + symbol_table.push_scope("FunctionBodyScope"); + match function_body { + FunctionBody::FunctionAliasBody(alias_body) => { + gather_node( + alias_body.as_node_ref(), + symbol_table, + fqn_context, + diagnostics, + ); + } + FunctionBody::FunctionEqualsBody(equals_body) => { + gather_node( + equals_body.as_node_ref(), + symbol_table, + fqn_context, + diagnostics, + ); + } + FunctionBody::FunctionBlockBody(block_body) => { + gather_node( + block_body.as_node_ref(), + symbol_table, + fqn_context, + diagnostics, + ); + } + } + symbol_table.pop_scope(); +} + +fn gather_member( + member: &Member, + symbol_table: &mut SymbolTable, + fqn_context: &mut FqnContext, + diagnostics: &mut Vec, +) { + let member_symbol = ClassMemberSymbol::new( + member.is_public(), + member.is_mut(), + member.identifier().name(), + Some(SourceDefinition::from_identifier(member.identifier())), + ); + if let Err(insert_error) = symbol_table.insert_class_member_symbol(member_symbol) { + handle_insert_error( + insert_error, + member.identifier().name(), + member.identifier().file_id(), + member.identifier().range(), + "Class Member", + diagnostics, + ); + } + gather_node( + member.type_use().as_node_ref(), + symbol_table, + fqn_context, + diagnostics, + ); +} + fn gather_variable_declaration( variable_declaration: &VariableDeclaration, symbol_table: &mut SymbolTable, diff --git a/src/name_analysis/symbol/class_member_symbol.rs b/src/name_analysis/symbol/class_member_symbol.rs index 8cd74f3..fc529de 100644 --- a/src/name_analysis/symbol/class_member_symbol.rs +++ b/src/name_analysis/symbol/class_member_symbol.rs @@ -3,32 +3,39 @@ use std::fmt::{Debug, Formatter}; #[derive(Clone)] pub struct ClassMemberSymbol { + is_public: bool, + is_mut: bool, declared_name: String, - is_field: bool, source_definition: Option, } impl ClassMemberSymbol { pub fn new( + is_public: bool, + is_mut: bool, declared_name: &str, - is_field: bool, source_definition: Option, ) -> Self { Self { + is_public, + is_mut, declared_name: declared_name.to_string(), - is_field, source_definition, } } + + pub fn is_public(&self) -> bool { + self.is_public + } + + pub fn is_mut(&self) -> bool { + self.is_mut + } pub fn declared_name(&self) -> &str { &self.declared_name } - pub fn is_field(&self) -> bool { - self.is_field - } - pub fn source_definition(&self) -> Option<&SourceDefinition> { self.source_definition.as_ref() } @@ -37,8 +44,9 @@ impl ClassMemberSymbol { impl Debug for ClassMemberSymbol { fn fmt(&self, f: &mut Formatter<'_>) -> std::fmt::Result { f.debug_struct("ClassMemberSymbol") + .field("is_public", &self.is_public) + .field("is_mut", &self.is_mut) .field("declared_name", &self.declared_name) - .field("is_field", &self.is_field) .field("source_definition", &self.source_definition) .finish() } diff --git a/src/name_analysis/symbol/source_definition.rs b/src/name_analysis/symbol/source_definition.rs index 60aeb0f..73a030b 100644 --- a/src/name_analysis/symbol/source_definition.rs +++ b/src/name_analysis/symbol/source_definition.rs @@ -1,7 +1,7 @@ use std::cell::RefCell; use std::range::Range; use std::rc::Rc; -use crate::ast::node::{Identifier, UseStatement}; +use crate::ast::node::{Identifier, Operator, UseStatement}; #[derive(Clone, Debug)] pub struct SourceDefinition { @@ -16,14 +16,6 @@ impl SourceDefinition { range: identifier.range(), } } - - pub fn from_identifier_rc(identifier: Rc>) -> Self { - let borrowed = identifier.borrow(); - SourceDefinition { - file_id: borrowed.file_id(), - range: borrowed.range(), - } - } pub fn from_use_statement(use_statement: &UseStatement) -> Self { Self { @@ -31,6 +23,13 @@ impl SourceDefinition { range: use_statement.range(), } } + + pub fn from_operator(operator: &Operator) -> Self { + Self { + file_id: operator.file_id(), + range: operator.range(), + } + } pub fn file_id(&self) -> usize { self.file_id diff --git a/src/name_analysis/symbol_table/mod.rs b/src/name_analysis/symbol_table/mod.rs index dec99b6..78fd325 100644 --- a/src/name_analysis/symbol_table/mod.rs +++ b/src/name_analysis/symbol_table/mod.rs @@ -57,11 +57,11 @@ impl SymbolTable { } fn current_scope(&self) -> &Scope { - self.scopes.last().unwrap() + &self.scopes[self.current_scope_id] } fn current_scope_mut(&mut self) -> &mut Scope { - self.scopes.last_mut().unwrap() + &mut self.scopes[self.current_scope_id] } fn find_current_scope_concrete_use_symbol( diff --git a/src/name_analysis/symbol_table/scope.rs b/src/name_analysis/symbol_table/scope.rs index 56bbee3..0b0c6fb 100644 --- a/src/name_analysis/symbol_table/scope.rs +++ b/src/name_analysis/symbol_table/scope.rs @@ -127,7 +127,13 @@ macro_rules! write_symbols { impl Display for Scope { fn fmt(&self, f: &mut Formatter<'_>) -> std::fmt::Result { - writeln!(f, "----Scope {} {}----", self.id(), self.debug_name())?; + writeln!( + f, + "----Scope {} (p: {}) {}----", + self.id(), + self.parent().map(|parent_id| format!("{}", parent_id)).unwrap_or_else(|| "None".to_string()), + self.debug_name() + )?; write_symbols!(f, self.concrete_use_symbols()); write_symbols!(f, self.star_use_symbols()); write_symbols!(f, self.module_symbols()); diff --git a/src/parser/ast.yaml b/src/parser/ast.yaml index ca177fc..df559fb 100644 --- a/src/parser/ast.yaml +++ b/src/parser/ast.yaml @@ -1,6 +1,18 @@ # $schema: ./ast.schema.yaml # Operators Operator: + struct: + children: + - inner: + member: + rule: OperatorInner + - file_id: + special: + kind: file_id + - range: + special: + kind: range +OperatorInner: leaf_enum: rules: - Or @@ -429,6 +441,30 @@ PlatformFunction: - identifier - parameters - return_type +PlatformOperatorFunction: + struct: + children: + - is_public: + member: + rule: Pub + build: + boolean: + on: rule_present + - platform_kw: + skip: + rule: Platform + - op_kw: + skip: + rule: Op + - generics: + member: + rule: GenericParameters + build: + node: + or_else_default: true + - operator + - parameters + - return_type InterfaceFunction: struct: children: diff --git a/src/parser/deimos.pest b/src/parser/deimos.pest index 4c65760..81cf3b8 100644 --- a/src/parser/deimos.pest +++ b/src/parser/deimos.pest @@ -131,6 +131,10 @@ Index = { "[]" } BorrowMut = { Borrow ~ Mut } Operator = { + OperatorInner +} + +OperatorInner = { Or | And | EqualTo @@ -431,6 +435,16 @@ PlatformFunction = { ~ ReturnType } +PlatformOperatorFunction = { + Pub? + ~ Platform + ~ Op + ~ GenericParameters? + ~ Operator + ~ Parameters + ~ ReturnType +} + InterfaceFunction = { Fn ~ GenericParameters?