Skip to content
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

Implement DelineatedPathExpression AST resolution #6309

Draft
wants to merge 1 commit into
base: master
Choose a base branch
from
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
24 changes: 23 additions & 1 deletion .vscode/launch.json
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,28 @@
"name": "Attach to forc-lsp",
"pid": "${command:pickProcess}",
"program": "${env:HOME}/.cargo/bin/forc-lsp"
}
},
{
"type": "lldb",
"request": "launch",
"name": "Debug executable 'forc'",
"cargo": {
"args": [
"build",
"--bin=forc",
"--package=forc"
],
"filter": {
"name": "forc",
"kind": "bin"
}
},
"args": [
"build",
"--path",
"const_rec"
],
"cwd": "${workspaceFolder}"
},
]
}
30 changes: 29 additions & 1 deletion sway-core/src/language/parsed/declaration.rs
Original file line number Diff line number Diff line change
Expand Up @@ -122,7 +122,7 @@ impl Declaration {
}
}

pub(crate) fn to_fn_ref(
pub(crate) fn to_fn_decl(
&self,
handler: &Handler,
engines: &Engines,
Expand Down Expand Up @@ -166,6 +166,34 @@ impl Declaration {
}
}

pub(crate) fn to_enum_decl(
&self,
handler: &Handler,
engines: &Engines,
) -> Result<ParsedDeclId<EnumDeclaration>, ErrorEmitted> {
match self {
Declaration::EnumDeclaration(decl_id) => Ok(*decl_id),
decl => Err(handler.emit_err(CompileError::DeclIsNotAnEnum {
actually: decl.friendly_type_name().to_string(),
span: decl.span(engines),
})),
}
}

pub(crate) fn to_const_decl(
&self,
handler: &Handler,
engines: &Engines,
) -> Result<ParsedDeclId<ConstantDeclaration>, ErrorEmitted> {
match self {
Declaration::ConstantDeclaration(decl_id) => Ok(*decl_id),
decl => Err(handler.emit_err(CompileError::DeclIsNotAConstant {
actually: decl.friendly_type_name().to_string(),
span: decl.span(engines),
})),
}
}

#[allow(unused)]
pub(crate) fn visibility(&self, decl_engine: &ParsedDeclEngine) -> Visibility {
match self {
Expand Down
4 changes: 4 additions & 0 deletions sway-core/src/language/parsed/declaration/struct.rs
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,8 @@ use crate::{
};
use sway_types::{ident::Ident, span::Span, Named, Spanned};

use super::ImplSelfOrTrait;

#[derive(Debug, Clone)]
pub struct StructDeclaration {
pub name: Ident,
Expand All @@ -15,6 +17,8 @@ pub struct StructDeclaration {
pub type_parameters: Vec<TypeParameter>,
pub visibility: Visibility,
pub(crate) span: Span,
// the impl blocks implementing this struct
pub impls: Vec<ImplSelfOrTrait>,
}

impl EqWithEngines for StructDeclaration {}
Expand Down
4 changes: 3 additions & 1 deletion sway-core/src/language/parsed/expression/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,7 @@ pub use method_name::MethodName;
pub use scrutinee::*;
use sway_ast::intrinsics::Intrinsic;

use super::{FunctionDeclaration, StructDeclaration};
use super::{Declaration, FunctionDeclaration, StructDeclaration};

/// Represents a parsed, but not yet type checked, [Expression](https://en.wikipedia.org/wiki/Expression_(computer_science)).
#[derive(Debug, Clone)]
Expand Down Expand Up @@ -295,6 +295,8 @@ impl PartialEqWithEngines for AmbiguousPathExpression {
#[derive(Debug, Clone)]
pub struct DelineatedPathExpression {
pub call_path_binding: TypeBinding<QualifiedCallPath>,
pub resolved_call_path_binding: Option<TypeBinding<ResolvedCallPath<Declaration>>>,

/// When args is equal to Option::None then it means that the
/// [DelineatedPathExpression] was initialized from an expression
/// that does not end with parenthesis.
Expand Down
15 changes: 11 additions & 4 deletions sway-core/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -36,6 +36,8 @@ pub use debug_generation::write_dwarf;
use indexmap::IndexMap;
use metadata::MetadataManager;
use query_engine::{ModuleCacheKey, ModuleCommonInfo, ParsedModuleInfo, ProgramsCacheEntry};
use semantic_analysis::symbol_resolve::ResolveSymbols;
use semantic_analysis::symbol_resolve_context::SymbolResolveContext;
use std::collections::hash_map::DefaultHasher;
use std::hash::{Hash, Hasher};
use std::path::{Path, PathBuf};
Expand Down Expand Up @@ -559,18 +561,23 @@ pub fn parsed_to_ast(
// Build the dependency graph for the submodules.
build_module_dep_graph(handler, &mut parse_program.root)?;

let namespace = Namespace::init_root(initial_namespace);
let initial_namespace = Namespace::init_root(initial_namespace);
// Collect the program symbols.
let mut collection_ctx =
ty::TyProgram::collect(handler, engines, parse_program, namespace.clone())?;
let namespace = initial_namespace.clone();
let mut collection_ctx = ty::TyProgram::collect(handler, engines, parse_program, namespace)?;

// println!("namespace {:#?}", collection_ctx.namespace);

let resolve_ctx = SymbolResolveContext::new(engines, &mut collection_ctx);
parse_program.resolve_symbols(handler, resolve_ctx);

// Type check the program.
let typed_program_opt = ty::TyProgram::type_check(
handler,
engines,
parse_program,
&mut collection_ctx,
namespace,
initial_namespace,
package_name,
build_config,
experimental,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -24,9 +24,11 @@ use crate::{
},
namespace::{IsExtendingExistingImpl, IsImplSelf, TraitMap, TryInsertingTraitImplOnFailure},
semantic_analysis::{
symbol_collection_context::SymbolCollectionContext, AbiMode, ConstShadowingMode,
TyNodeDepGraphNodeId, TypeCheckAnalysis, TypeCheckAnalysisContext, TypeCheckContext,
TypeCheckFinalization, TypeCheckFinalizationContext,
symbol_collection_context::SymbolCollectionContext,
type_resolve::{resolve_type, VisibilityCheck},
AbiMode, ConstShadowingMode, TyNodeDepGraphNodeId, TypeCheckAnalysis,
TypeCheckAnalysisContext, TypeCheckContext, TypeCheckFinalization,
TypeCheckFinalizationContext,
},
type_system::*,
};
Expand All @@ -38,15 +40,22 @@ impl TyImplSelfOrTrait {
ctx: &mut SymbolCollectionContext,
decl_id: &ParsedDeclId<ImplSelfOrTrait>,
) -> Result<(), ErrorEmitted> {
let impl_trait = engines.pe().get_impl_self_or_trait(decl_id);
let mut impl_trait = engines
.pe()
.get_impl_self_or_trait(decl_id)
.as_ref()
.clone();

let decl = Declaration::ImplSelfOrTrait(*decl_id);
ctx.insert_parsed_symbol(
handler,
engines,
impl_trait.trait_name.suffix.clone(),
decl.clone(),
)?;

if !impl_trait.is_self {
ctx.insert_parsed_symbol(
handler,
engines,
impl_trait.trait_name.suffix.clone(),
decl.clone(),
)?;
}

let _ = ctx.scoped(
engines,
Expand All @@ -67,6 +76,33 @@ impl TyImplSelfOrTrait {
Ok(())
},
);

// println!(
// "impl type id {:?}",
// engines.help_out(impl_trait.implementing_for.type_id)
// );

impl_trait.implementing_for.type_id = resolve_type(
handler,
engines,
&ctx.namespace,
ctx.namespace.mod_path(),
impl_trait.implementing_for.type_id,
&impl_trait.implementing_for.span,
EnforceTypeArguments::Yes,
None,
None,
&SubstTypesContext::dummy(engines),
VisibilityCheck::No,
)?;

// println!(
// "after impl type id resolve {:?}",
// engines.help_out(impl_trait.implementing_for.type_id)
// );

engines.pe().replace(*decl_id, impl_trait);

Ok(())
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -448,6 +448,7 @@ impl ty::TyExpression {
ExpressionKind::DelineatedPath(delineated_path_expression) => {
let DelineatedPathExpression {
call_path_binding,
resolved_call_path_binding: _,
args,
} = *delineated_path_expression.clone();
Self::type_check_delineated_path(
Expand Down
1 change: 1 addition & 0 deletions sway-core/src/semantic_analysis/node_dependencies.rs
Original file line number Diff line number Diff line change
Expand Up @@ -634,6 +634,7 @@ impl Dependencies {
ExpressionKind::DelineatedPath(delineated_path_expression) => {
let DelineatedPathExpression {
call_path_binding,
resolved_call_path_binding: _,
args,
} = &**delineated_path_expression;
// It's either a module path which we can ignore, or an enum variant path, in which
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@ use sway_types::{span::Span, Ident};

use super::{ConstShadowingMode, GenericShadowingMode};

#[derive(Clone)]
//#[derive(Clone)]
/// Contextual state tracked and accumulated throughout symbol collecting.
pub struct SymbolCollectionContext {
/// The namespace context accumulated throughout symbol collecting.
Expand Down
59 changes: 38 additions & 21 deletions sway-core/src/semantic_analysis/symbol_resolve.rs
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,7 @@ use crate::{
},
CallPath, CallPathTree, ResolvedCallPath,
},
TraitConstraint, TypeArgument, TypeBinding, TypeParameter,
TraitConstraint, TypeArgs, TypeArgument, TypeBinding, TypeParameter,
};

use super::symbol_resolve_context::SymbolResolveContext;
Expand Down Expand Up @@ -495,23 +495,14 @@ impl ResolveSymbols for StructScrutineeField {
}

impl ResolveSymbols for Expression {
fn resolve_symbols(&mut self, handler: &Handler, ctx: SymbolResolveContext) {
self.kind.resolve_symbols(handler, ctx);
}
}

impl ResolveSymbols for ExpressionKind {
fn resolve_symbols(&mut self, handler: &Handler, mut ctx: SymbolResolveContext) {
match self {
match &mut self.kind {
ExpressionKind::Error(_, _) => {}
ExpressionKind::Literal(_) => {}
ExpressionKind::AmbiguousPathExpression(_) => {}
ExpressionKind::FunctionApplication(expr) => {
let result = SymbolResolveTypeBinding::resolve_symbol(
&mut expr.call_path_binding,
&Handler::default(),
ctx.by_ref(),
);
let result = expr.call_path_binding.resolve_symbol(handler, ctx.by_ref());

if let Ok(result) = result {
expr.resolved_call_path_binding = Some(TypeBinding::<
ResolvedCallPath<ParsedDeclId<FunctionDeclaration>>,
Expand Down Expand Up @@ -547,13 +538,11 @@ impl ResolveSymbols for ExpressionKind {
.iter_mut()
.for_each(|e| e.resolve_symbols(handler, ctx.by_ref())),
ExpressionKind::Struct(expr) => {
expr.call_path_binding
.resolve_symbols(handler, ctx.by_ref());
let result = SymbolResolveTypeBinding::resolve_symbol(
&mut expr.call_path_binding,
&Handler::default(),
ctx.by_ref(),
);
// expr.call_path_binding
// .resolve_symbols(handler, ctx.by_ref());

let result = expr.call_path_binding.resolve_symbol(handler, ctx.by_ref());

if let Ok(result) = result {
expr.resolved_call_path_binding = Some(TypeBinding::<
ResolvedCallPath<ParsedDeclId<StructDeclaration>>,
Expand Down Expand Up @@ -604,7 +593,22 @@ impl ResolveSymbols for ExpressionKind {
}
ExpressionKind::Subfield(expr) => expr.prefix.resolve_symbols(handler, ctx),
ExpressionKind::DelineatedPath(expr) => {
expr.call_path_binding.resolve_symbols(handler, ctx)
let result =
expr.call_path_binding
.resolve_symbol(handler, ctx.by_ref(), self.span.clone());

if let Ok(_result) = result {
// expr.resolved_call_path_binding = Some(TypeBinding::<
// ResolvedCallPath<ParsedDeclId<StructDeclaration>>,
// > {
// inner: ResolvedCallPath {
// decl: result,
// unresolved_call_path: expr.call_path_binding.inner.clone(),
// },
// span: expr.call_path_binding.span.clone(),
// type_arguments: expr.call_path_binding.type_arguments.clone(),
// });
}
}
ExpressionKind::AbiCast(expr) => {
expr.abi_name.resolve_symbols(handler, ctx.by_ref());
Expand Down Expand Up @@ -644,3 +648,16 @@ impl ResolveSymbols for ExpressionKind {
}
}
}

impl<T> ResolveSymbols for TypeBinding<T> {
fn resolve_symbols(&mut self, handler: &Handler, mut ctx: SymbolResolveContext) {
match self.type_arguments {
TypeArgs::Regular(ref mut args) => args
.iter_mut()
.for_each(|arg| arg.resolve_symbols(handler, ctx.by_ref())),
TypeArgs::Prefix(ref mut args) => args
.iter_mut()
.for_each(|arg| arg.resolve_symbols(handler, ctx.by_ref())),
}
}
}
24 changes: 21 additions & 3 deletions sway-core/src/semantic_analysis/symbol_resolve_context.rs
Original file line number Diff line number Diff line change
@@ -1,16 +1,16 @@
use crate::{
engine_threading::*,
language::{CallPath, Visibility},
language::{CallPath, QualifiedCallPath, Visibility},
namespace::ResolvedDeclaration,
semantic_analysis::{ast_node::ConstShadowingMode, Namespace},
type_system::TypeId,
type_system::TypeId, SubstTypesContext,
};
use sway_error::handler::{ErrorEmitted, Handler};
use sway_types::{span::Span, Ident};

use super::{
symbol_collection_context::SymbolCollectionContext,
type_resolve::{resolve_call_path, VisibilityCheck},
type_resolve::{resolve_call_path, resolve_qualified_call_path, VisibilityCheck},
GenericShadowingMode,
};

Expand Down Expand Up @@ -194,4 +194,22 @@ impl<'a> SymbolResolveContext<'a> {
VisibilityCheck::Yes,
)
}

/// Short-hand for calling [Root::resolve_qualified_call_path_with_visibility_check] on `root` with the `mod_path`.
pub(crate) fn resolve_qualified_call_path_with_visibility_check(
&self,
handler: &Handler,
qualified_call_path: &QualifiedCallPath,
) -> Result<ResolvedDeclaration, ErrorEmitted> {
resolve_qualified_call_path(
handler,
self.engines(),
self.namespace(),
&self.namespace().mod_path.clone(),
qualified_call_path,
self.self_type(),
&SubstTypesContext::dummy(self.engines()),
VisibilityCheck::Yes,
)
}
}
Loading
Loading