Compare commits

..

2 Commits

Author SHA1 Message Date
Jesse Brault
d50cc24d0a Work on constructor with new lowering api. WIP. 2026-05-04 14:02:34 -05:00
Jesse Brault
1bd1e5c23a Work on classes and lowering to IR. WIP. 2026-05-01 14:53:01 -05:00
10 changed files with 287 additions and 23 deletions

View File

@ -11,7 +11,7 @@ use crate::ast::helpers::{
resolve_ctor_name, resolve_ctor_name,
}; };
use crate::ast::statement::Statement; use crate::ast::statement::Statement;
use crate::ast::{NodeId, NodesToSymbols}; use crate::ast::{FunctionReturnTypes, NodeId, NodesToSymbols, NodesToTypes, SymbolsToTypes};
use crate::diagnostic::{Diagnostic, Diagnostics}; use crate::diagnostic::{Diagnostic, Diagnostics};
use crate::error_codes::{FIELD_MULTIPLE_INIT, FIELD_UNINIT}; use crate::error_codes::{FIELD_MULTIPLE_INIT, FIELD_UNINIT};
use crate::ir::ir_class::{IrClass, IrField}; use crate::ir::ir_class::{IrClass, IrField};
@ -187,6 +187,7 @@ impl Class {
(names_table, diagnostics) (names_table, diagnostics)
} }
#[deprecated]
pub fn check_names(&self, symbol_table: &SymbolTable) -> Vec<Diagnostic> { pub fn check_names(&self, symbol_table: &SymbolTable) -> Vec<Diagnostic> {
let mut diagnostics: Vec<Diagnostic> = Vec::new(); let mut diagnostics: Vec<Diagnostic> = Vec::new();
@ -231,6 +232,7 @@ impl Class {
.collect() .collect()
} }
#[deprecated]
pub fn analyze_local_names(&self, symbol_table: &mut SymbolTable) -> Vec<Diagnostic> { pub fn analyze_local_names(&self, symbol_table: &mut SymbolTable) -> Vec<Diagnostic> {
let class_symbol = self.get_class_symbol_owned(symbol_table); let class_symbol = self.get_class_symbol_owned(symbol_table);
let mut diagnostics: Vec<Diagnostic> = Vec::new(); let mut diagnostics: Vec<Diagnostic> = Vec::new();
@ -244,6 +246,7 @@ impl Class {
diagnostics diagnostics
} }
#[deprecated]
pub fn gather_types( pub fn gather_types(
&self, &self,
symbol_table: &SymbolTable, symbol_table: &SymbolTable,
@ -472,6 +475,7 @@ impl Class {
Ok(()) Ok(())
} }
#[deprecated]
pub fn type_check( pub fn type_check(
&mut self, &mut self,
symbol_table: &SymbolTable, symbol_table: &SymbolTable,
@ -485,6 +489,7 @@ impl Class {
Ok(()) Ok(())
} }
#[deprecated]
pub fn to_ir( pub fn to_ir(
&self, &self,
symbol_table: &SymbolTable, symbol_table: &SymbolTable,
@ -529,4 +534,43 @@ impl Class {
(ir_class, ir_functions) (ir_class, ir_functions)
} }
pub fn lower_to_ir(
&self,
nodes_to_symbols: &NodesToSymbols,
symbols_to_types: &SymbolsToTypes,
nodes_to_types: &NodesToTypes,
function_return_types: &FunctionReturnTypes,
) -> (IrClass, Vec<IrFunction>) {
let mut ir_functions = Vec::new();
if let Some(constructor) = &self.constructor {
// todo
}
for function in &self.functions {
ir_functions.push(function.lower_to_ir_static(
nodes_to_symbols,
symbols_to_types,
nodes_to_types,
function_return_types,
));
}
let self_class_symbol = nodes_to_symbols
.get(&self.node_id)
.unwrap()
.unwrap_class_symbol();
let ir_class = IrClass::new(
self_class_symbol.declared_name_owned(),
fqn_parts_to_string(self_class_symbol.fqn_parts()).into(),
self.fields
.iter()
.map(|field| field.lower_to_ir_field(nodes_to_symbols, symbols_to_types))
.collect(),
);
(ir_class, ir_functions)
}
} }

View File

@ -245,7 +245,7 @@ impl CompilationUnit {
diagnostics_result!(diagnostics) diagnostics_result!(diagnostics)
} }
pub fn lower( pub fn lower_to_ir(
&self, &self,
nodes_to_symbols: &NodesToSymbols, nodes_to_symbols: &NodesToSymbols,
symbols_to_types: &SymbolsToTypes, symbols_to_types: &SymbolsToTypes,
@ -256,7 +256,7 @@ impl CompilationUnit {
let mut ir_functions = Vec::new(); let mut ir_functions = Vec::new();
for function in &self.functions { for function in &self.functions {
ir_functions.push(function.lower_static( ir_functions.push(function.lower_to_ir_static(
nodes_to_symbols, nodes_to_symbols,
symbols_to_types, symbols_to_types,
nodes_to_types, nodes_to_types,
@ -264,9 +264,21 @@ impl CompilationUnit {
)); ));
} }
for class in &self.classes {
let (ir_class, mut class_ir_functions) = class.lower_to_ir(
nodes_to_symbols,
symbols_to_types,
nodes_to_types,
function_return_types,
);
ir_classes.push(ir_class);
ir_functions.append(&mut class_ir_functions);
}
(ir_classes, ir_functions) (ir_classes, ir_functions)
} }
#[deprecated]
pub fn to_ir( pub fn to_ir(
&self, &self,
symbol_table: &SymbolTable, symbol_table: &SymbolTable,

View File

@ -1,4 +1,3 @@
use crate::ast::NodesToSymbols;
use crate::ast::field::Field; use crate::ast::field::Field;
use crate::ast::fqn_context::FqnContext; use crate::ast::fqn_context::FqnContext;
use crate::ast::fqn_util::fqn_parts_to_string; use crate::ast::fqn_util::fqn_parts_to_string;
@ -8,6 +7,7 @@ use crate::ast::helpers::{
use crate::ast::ir_builder::IrBuilder; use crate::ast::ir_builder::IrBuilder;
use crate::ast::parameter::Parameter; use crate::ast::parameter::Parameter;
use crate::ast::statement::Statement; use crate::ast::statement::Statement;
use crate::ast::{NodeId, NodesToSymbols, NodesToTypes, SymbolsToTypes};
use crate::diagnostic::{Diagnostic, Diagnostics}; use crate::diagnostic::{Diagnostic, Diagnostics};
use crate::ir::ir_allocate::IrAllocate; use crate::ir::ir_allocate::IrAllocate;
use crate::ir::ir_assign::IrAssign; use crate::ir::ir_assign::IrAssign;
@ -34,6 +34,7 @@ use std::ops::Neg;
use std::rc::Rc; use std::rc::Rc;
pub struct Constructor { pub struct Constructor {
node_id: NodeId,
is_public: bool, is_public: bool,
ctor_keyword_source_range: SourceRange, ctor_keyword_source_range: SourceRange,
parameters: Vec<Parameter>, parameters: Vec<Parameter>,
@ -43,12 +44,14 @@ pub struct Constructor {
impl Constructor { impl Constructor {
pub fn new( pub fn new(
node_id: NodeId,
is_public: bool, is_public: bool,
ctor_keyword_source_range: SourceRange, ctor_keyword_source_range: SourceRange,
parameters: Vec<Parameter>, parameters: Vec<Parameter>,
statements: Vec<Statement>, statements: Vec<Statement>,
) -> Self { ) -> Self {
Self { Self {
node_id,
is_public, is_public,
ctor_keyword_source_range, ctor_keyword_source_range,
parameters, parameters,
@ -123,6 +126,7 @@ impl Constructor {
(names_table, diagnostics) (names_table, diagnostics)
} }
#[deprecated]
pub fn check_names(&self, symbol_table: &SymbolTable) -> Vec<Diagnostic> { pub fn check_names(&self, symbol_table: &SymbolTable) -> Vec<Diagnostic> {
let mut diagnostics: Vec<Diagnostic> = Vec::new(); let mut diagnostics: Vec<Diagnostic> = Vec::new();
for parameter in &self.parameters { for parameter in &self.parameters {
@ -131,6 +135,7 @@ impl Constructor {
diagnostics diagnostics
} }
#[deprecated]
pub fn analyze_local_names( pub fn analyze_local_names(
&self, &self,
symbol_table: &mut SymbolTable, symbol_table: &mut SymbolTable,
@ -142,12 +147,14 @@ impl Constructor {
.collect() .collect()
} }
#[deprecated]
pub fn gather_types_into(&self, symbol_table: &SymbolTable, types_table: &mut TypesTable) { pub fn gather_types_into(&self, symbol_table: &SymbolTable, types_table: &mut TypesTable) {
for parameter in &self.parameters { for parameter in &self.parameters {
parameter.gather_types_into(symbol_table, types_table); parameter.gather_types_into(symbol_table, types_table);
} }
} }
#[deprecated]
pub fn type_check( pub fn type_check(
&mut self, &mut self,
symbol_table: &SymbolTable, symbol_table: &SymbolTable,
@ -180,6 +187,7 @@ impl Constructor {
} }
} }
#[deprecated]
pub fn to_ir( pub fn to_ir(
&self, &self,
class_symbol: &Rc<ClassSymbol>, class_symbol: &Rc<ClassSymbol>,
@ -315,4 +323,139 @@ impl Constructor {
entry_block.clone(), entry_block.clone(),
) )
} }
pub fn lower_to_ir(
&self,
class_symbol: &Rc<ClassSymbol>,
fields: &[Field],
nodes_to_symbols: &NodesToSymbols,
symbols_to_types: &SymbolsToTypes,
nodes_to_types: &NodesToTypes,
) -> IrFunction {
let mut ir_builder = IrBuilder::new();
// gather ir_parameters
let mut ir_parameters = Vec::new();
let base_offset = (self.parameters.len() as isize).neg();
for (i, parameter) in self.parameters.iter().enumerate() {
let symbol = nodes_to_symbols.get(&parameter.node_id()).unwrap();
let parameter_type = symbols_to_types.get(symbol).unwrap();
let offset = base_offset + i as isize;
let ir_parameter = Rc::new(IrParameter::new(
symbol.declared_name(),
parameter_type.clone(),
offset,
));
// save in builder
ir_builder.push_parameter(symbol.unwrap_parameter_symbol(), ir_parameter.clone());
// push for saving to IrFunction
ir_parameters.push(ir_parameter);
}
// entry-block
let entry_block_id = ir_builder.new_block();
// PART 1: Make self object
let self_variable = Rc::new(RefCell::new(IrVariable::new_vr(
ir_builder.new_t_var().into(),
ir_builder.current_block().id(),
&TypeInfo::ParameterizedClass(class_symbol.clone(), Vec::new()), // todo: figure out the correct TypeInfo for this
)));
// save self variable in builder
ir_builder
.set_self_parameter_or_variable(IrParameterOrVariable::Variable(self_variable.clone()));
// allocate the self object
let ir_assign = IrAssign::new(
self_variable.clone(),
IrOperation::Allocate(IrAllocate::new(class_symbol.declared_name_owned())),
);
ir_builder
.current_block_mut()
.add_statement(IrStatement::Assign(ir_assign));
// PART 2: Initialize fields that are initialized OUTSIDE the constructor
for field in fields {
if let Some(initializer) = field.initializer() {
let symbol = nodes_to_symbols.get(&field.node_id()).unwrap();
let field_type = symbols_to_types.get(symbol).unwrap();
let field_symbol = symbol.unwrap_field_symbol();
// 1. Get a mut ref to the field
// mut t_var: Type = &mut self.x
let ir_get_field_ref_mut = IrGetFieldRefMut::new(
IrParameterOrVariable::Variable(self_variable.clone()),
field_symbol.field_index(),
);
let field_ref_mut_ir_variable = Rc::new(RefCell::new(IrVariable::new_vr(
ir_builder.new_t_var().into(),
ir_builder.current_block().id(),
field_type,
)));
let ir_assign = IrAssign::new(
field_ref_mut_ir_variable.clone(),
IrOperation::GetFieldRefMut(ir_get_field_ref_mut),
);
ir_builder
.current_block_mut()
.add_statement(IrStatement::Assign(ir_assign));
// save the mut ref for later uses if needed
ir_builder.field_mut_pointer_variables_mut().insert(
field.declared_name_owned(),
field_ref_mut_ir_variable.clone(),
);
// 2. Evaluate initializer and save result to mut field ref
let ir_expression = initializer.lower_to_ir_expression(
&mut ir_builder,
nodes_to_symbols,
symbols_to_types,
nodes_to_types,
);
let ir_set_field = IrSetField::new(&field_ref_mut_ir_variable, ir_expression);
ir_builder
.current_block_mut()
.add_statement(IrStatement::SetField(ir_set_field));
}
}
// PART 3. Constructor statements
for statement in &self.statements {
statement.lower(
&mut ir_builder,
nodes_to_symbols,
symbols_to_types,
nodes_to_types,
false,
);
}
// PART 4. Return finished self object
let ir_return_statement = IrStatement::Return(IrReturn::new(Some(IrExpression::Variable(
self_variable.clone(),
))));
ir_builder
.current_block_mut()
.add_statement(ir_return_statement);
// Finish up the builder and return IrFunction
ir_builder.finish_block();
let entry_block = ir_builder.get_block(entry_block_id);
let constructor_symbol = nodes_to_symbols
.get(&self.node_id)
.unwrap()
.unwrap_constructor_symbol();
IrFunction::new(
fqn_parts_to_string(constructor_symbol.fqn_parts()),
ir_parameters,
&TypeInfo::Class(class_symbol.clone()), // TODO
entry_block.clone(),
)
}
} }

View File

@ -1,9 +1,10 @@
use crate::ast::NodesToSymbols;
use crate::ast::expression::Expression; use crate::ast::expression::Expression;
use crate::ast::helpers::insert_resolved_names_into; use crate::ast::helpers::insert_resolved_names_into;
use crate::ast::type_use::TypeUse; use crate::ast::type_use::TypeUse;
use crate::ast::{NodeId, NodesToSymbols, SymbolsToTypes};
use crate::diagnostic::{Diagnostic, Diagnostics}; use crate::diagnostic::{Diagnostic, Diagnostics};
use crate::diagnostic_factories::field_has_no_type_or_init; use crate::diagnostic_factories::field_has_no_type_or_init;
use crate::ir::ir_class::IrField;
use crate::source_range::SourceRange; use crate::source_range::SourceRange;
use crate::symbol::class_symbol::ClassSymbol; use crate::symbol::class_symbol::ClassSymbol;
use crate::symbol::field_symbol::FieldSymbol; use crate::symbol::field_symbol::FieldSymbol;
@ -12,6 +13,7 @@ use crate::types_table::TypesTable;
use std::rc::Rc; use std::rc::Rc;
pub struct Field { pub struct Field {
node_id: NodeId,
declared_name: Rc<str>, declared_name: Rc<str>,
declared_name_source_range: SourceRange, declared_name_source_range: SourceRange,
is_public: bool, is_public: bool,
@ -23,6 +25,7 @@ pub struct Field {
impl Field { impl Field {
pub fn new( pub fn new(
node_id: NodeId,
declared_name: &str, declared_name: &str,
declared_name_source_range: SourceRange, declared_name_source_range: SourceRange,
is_public: bool, is_public: bool,
@ -31,6 +34,7 @@ impl Field {
initializer: Option<Expression>, initializer: Option<Expression>,
) -> Self { ) -> Self {
Self { Self {
node_id,
declared_name: declared_name.into(), declared_name: declared_name.into(),
declared_name_source_range, declared_name_source_range,
is_public, is_public,
@ -41,6 +45,10 @@ impl Field {
} }
} }
pub fn node_id(&self) -> NodeId {
self.node_id
}
pub fn declared_name(&self) -> &str { pub fn declared_name(&self) -> &str {
&self.declared_name &self.declared_name
} }
@ -215,4 +223,18 @@ impl Field {
None => Ok(()), None => Ok(()),
} }
} }
pub fn lower_to_ir_field(
&self,
nodes_to_symbols: &NodesToSymbols,
symbols_to_types: &SymbolsToTypes,
) -> IrField {
let symbol = nodes_to_symbols.get(&self.node_id).unwrap();
let field_type = symbols_to_types.get(symbol).unwrap();
IrField::new(
self.declared_name.clone(),
symbol.unwrap_field_symbol().field_index(), // todo: this needs to be stored NOT in the symbol
field_type.clone(),
)
}
} }

View File

@ -18,6 +18,7 @@ use crate::source_range::SourceRange;
use crate::symbol::Symbol; use crate::symbol::Symbol;
use crate::symbol::class_symbol::ClassSymbol; use crate::symbol::class_symbol::ClassSymbol;
use crate::symbol::function_symbol::FunctionSymbol; use crate::symbol::function_symbol::FunctionSymbol;
use crate::symbol::parameter_symbol::ParameterSymbol;
use crate::symbol_table::SymbolTable; use crate::symbol_table::SymbolTable;
use crate::type_info::TypeInfo; use crate::type_info::TypeInfo;
use crate::types_table::TypesTable; use crate::types_table::TypesTable;
@ -33,7 +34,8 @@ pub struct Function {
parameters: Vec<Parameter>, parameters: Vec<Parameter>,
return_type: Option<TypeUse>, return_type: Option<TypeUse>,
statements: Vec<Statement>, statements: Vec<Statement>,
scope_id: Option<usize>, container_scope_id: Option<usize>,
function_scope_id: Option<usize>,
} }
impl Function { impl Function {
@ -54,7 +56,8 @@ impl Function {
parameters, parameters,
return_type, return_type,
statements, statements,
scope_id: None, container_scope_id: None,
function_scope_id: None,
} }
} }
@ -71,9 +74,10 @@ impl Function {
} }
pub fn init_scopes(&mut self, symbol_table: &mut SymbolTable, container_scope: usize) { pub fn init_scopes(&mut self, symbol_table: &mut SymbolTable, container_scope: usize) {
self.scope_id = Some(container_scope); self.container_scope_id = Some(container_scope);
let function_scope = let function_scope =
symbol_table.push_function_scope(&format!("function_scope({})", self.declared_name)); symbol_table.push_function_scope(&format!("function_scope({})", self.declared_name));
self.function_scope_id = Some(function_scope);
for parameter in &mut self.parameters { for parameter in &mut self.parameters {
parameter.init_scopes(symbol_table, function_scope); parameter.init_scopes(symbol_table, function_scope);
@ -102,6 +106,17 @@ impl Function {
let mut all_symbols: Vec<Symbol> = vec![]; let mut all_symbols: Vec<Symbol> = vec![];
let mut parameter_symbols = Vec::new(); let mut parameter_symbols = Vec::new();
if is_method {
let self_parameter_symbol = Rc::new(ParameterSymbol::new(
&Rc::from("self"),
None,
self.function_scope_id.unwrap(),
));
parameter_symbols.push(self_parameter_symbol.clone());
all_symbols.push(Symbol::Parameter(self_parameter_symbol))
}
collect_parameter_symbols_into(&self.parameters, &mut all_symbols, &mut parameter_symbols); collect_parameter_symbols_into(&self.parameters, &mut all_symbols, &mut parameter_symbols);
let function_symbol = Rc::new(FunctionSymbol::new( let function_symbol = Rc::new(FunctionSymbol::new(
@ -110,7 +125,7 @@ impl Function {
fqn_context.resolve(self.declared_name()), fqn_context.resolve(self.declared_name()),
false, false,
is_method, is_method,
self.scope_id.unwrap(), self.container_scope_id.unwrap(),
parameter_symbols, parameter_symbols,
)); ));
all_symbols.push(Symbol::Function(function_symbol.clone())); all_symbols.push(Symbol::Function(function_symbol.clone()));
@ -239,7 +254,7 @@ impl Function {
#[deprecated] #[deprecated]
pub fn gather_types(&self, symbol_table: &SymbolTable, types_table: &mut TypesTable) { pub fn gather_types(&self, symbol_table: &SymbolTable, types_table: &mut TypesTable) {
let function_symbol = symbol_table let function_symbol = symbol_table
.get_function_symbol_owned(self.scope_id.unwrap(), self.declared_name()) .get_function_symbol_owned(self.container_scope_id.unwrap(), self.declared_name())
.unwrap(); .unwrap();
// self type (the signature) // self type (the signature)
@ -336,7 +351,7 @@ impl Function {
) -> Result<(), Vec<Diagnostic>> { ) -> Result<(), Vec<Diagnostic>> {
let mut diagnostics = vec![]; let mut diagnostics = vec![];
let function_symbol = symbol_table let function_symbol = symbol_table
.get_function_symbol(self.scope_id.unwrap(), self.declared_name()) .get_function_symbol(self.container_scope_id.unwrap(), self.declared_name())
.unwrap(); .unwrap();
// parameters // parameters
@ -408,6 +423,7 @@ impl Function {
} }
} }
#[deprecated]
pub fn to_ir( pub fn to_ir(
&self, &self,
symbol_table: &SymbolTable, symbol_table: &SymbolTable,
@ -416,7 +432,7 @@ impl Function {
) -> IrFunction { ) -> IrFunction {
let mut builder = IrBuilder::new(); let mut builder = IrBuilder::new();
let function_symbol = symbol_table let function_symbol = symbol_table
.get_function_symbol(self.scope_id.unwrap(), self.declared_name()) .get_function_symbol(self.container_scope_id.unwrap(), self.declared_name())
.unwrap(); .unwrap();
// parameters // parameters
@ -441,7 +457,7 @@ impl Function {
) )
} }
pub fn lower_static( pub fn lower_to_ir_static(
&self, &self,
nodes_to_symbols: &NodesToSymbols, nodes_to_symbols: &NodesToSymbols,
symbols_to_types: &SymbolsToTypes, symbols_to_types: &SymbolsToTypes,

View File

@ -52,7 +52,7 @@ impl Parameter {
pub fn make_symbol(&self) -> ParameterSymbol { pub fn make_symbol(&self) -> ParameterSymbol {
ParameterSymbol::new( ParameterSymbol::new(
&self.declared_name, &self.declared_name,
self.declared_name_source_range.clone(), Some(self.declared_name_source_range.clone()),
self.scope_id.unwrap(), self.scope_id.unwrap(),
) )
} }

View File

@ -848,6 +848,7 @@ impl<'a> Parser<'a> {
if let Some(ctor_keyword) = ctor_keyword { if let Some(ctor_keyword) = ctor_keyword {
let constructor = Constructor::new( let constructor = Constructor::new(
self.next_node_id(),
is_public, is_public,
SourceRange::new(ctor_keyword.start(), ctor_keyword.end()), SourceRange::new(ctor_keyword.start(), ctor_keyword.end()),
parameters, parameters,
@ -899,6 +900,7 @@ impl<'a> Parser<'a> {
if let Some(identifier) = identifier { if let Some(identifier) = identifier {
let field = Field::new( let field = Field::new(
self.next_node_id(),
self.token_text(&identifier), self.token_text(&identifier),
SourceRange::new(identifier.start(), identifier.end()), SourceRange::new(identifier.start(), identifier.end()),
is_public, is_public,

View File

@ -36,7 +36,7 @@ impl ExpressibleSymbol {
Some(function_symbol.declared_name_source_range()) Some(function_symbol.declared_name_source_range())
} }
ExpressibleSymbol::Parameter(parameter_symbol) => { ExpressibleSymbol::Parameter(parameter_symbol) => {
Some(parameter_symbol.declared_name_source_range()) parameter_symbol.declared_name_source_range()
} }
ExpressibleSymbol::Variable(variable_symbol) => { ExpressibleSymbol::Variable(variable_symbol) => {
Some(variable_symbol.declared_name_source_range()) Some(variable_symbol.declared_name_source_range())

View File

@ -72,9 +72,7 @@ impl Symbol {
Some(constructor_symbol.declared_name_source_range()) Some(constructor_symbol.declared_name_source_range())
} }
Symbol::Function(function_symbol) => Some(function_symbol.declared_name_source_range()), Symbol::Function(function_symbol) => Some(function_symbol.declared_name_source_range()),
Symbol::Parameter(parameter_symbol) => { Symbol::Parameter(parameter_symbol) => parameter_symbol.declared_name_source_range(),
Some(parameter_symbol.declared_name_source_range())
}
Symbol::Variable(variable_symbol) => Some(variable_symbol.declared_name_source_range()), Symbol::Variable(variable_symbol) => Some(variable_symbol.declared_name_source_range()),
} }
} }
@ -119,4 +117,32 @@ impl Symbol {
_ => panic!(), _ => panic!(),
} }
} }
pub fn unwrap_class_symbol(&self) -> &Rc<ClassSymbol> {
match self {
Symbol::Class(class_symbol) => class_symbol,
_ => panic!(),
}
}
pub fn unwrap_field_symbol(&self) -> &Rc<FieldSymbol> {
match self {
Symbol::Field(field_symbol) => field_symbol,
_ => panic!(),
}
}
pub fn unwrap_parameter_symbol(&self) -> &Rc<ParameterSymbol> {
match self {
Symbol::Parameter(parameter_symbol) => parameter_symbol,
_ => panic!(),
}
}
pub fn unwrap_constructor_symbol(&self) -> &Rc<ConstructorSymbol> {
match self {
Symbol::Constructor(constructor_symbol) => constructor_symbol,
_ => panic!(),
}
}
} }

View File

@ -1,18 +1,17 @@
use crate::source_range::SourceRange; use crate::source_range::SourceRange;
use crate::symbol::Symbol;
use std::hash::{Hash, Hasher}; use std::hash::{Hash, Hasher};
use std::rc::Rc; use std::rc::Rc;
pub struct ParameterSymbol { pub struct ParameterSymbol {
declared_name: Rc<str>, declared_name: Rc<str>,
declared_name_source_range: SourceRange, declared_name_source_range: Option<SourceRange>,
scope_id: usize, scope_id: usize,
} }
impl ParameterSymbol { impl ParameterSymbol {
pub fn new( pub fn new(
declared_name: &Rc<str>, declared_name: &Rc<str>,
declared_name_source_range: SourceRange, declared_name_source_range: Option<SourceRange>,
scope_id: usize, scope_id: usize,
) -> Self { ) -> Self {
Self { Self {
@ -30,8 +29,8 @@ impl ParameterSymbol {
self.declared_name.clone() self.declared_name.clone()
} }
pub fn declared_name_source_range(&self) -> &SourceRange { pub fn declared_name_source_range(&self) -> Option<&SourceRange> {
&self.declared_name_source_range self.declared_name_source_range.as_ref()
} }
pub fn scope_id(&self) -> usize { pub fn scope_id(&self) -> usize {