From 3a623acaf70c934ee9dbd74dfadcaa2c612160c5 Mon Sep 17 00:00:00 2001 From: Nadrieril Date: Sun, 6 Dec 2020 20:10:51 +0000 Subject: Make global store of imports and import results --- dhall/Cargo.toml | 1 + dhall/src/ctxt.rs | 109 +++++++++++++++++++++++++++++++ dhall/src/lib.rs | 3 + dhall/src/semantics/resolve/env.rs | 37 +++++------ dhall/src/semantics/resolve/resolve.rs | 113 ++++++++++++++++++++------------- 5 files changed, 201 insertions(+), 62 deletions(-) create mode 100644 dhall/src/ctxt.rs (limited to 'dhall') diff --git a/dhall/Cargo.toml b/dhall/Cargo.toml index 1b4f9a3..1e9cfbc 100644 --- a/dhall/Cargo.toml +++ b/dhall/Cargo.toml @@ -21,6 +21,7 @@ path = "tests/spec.rs" [dependencies] annotate-snippets = "0.9.0" +elsa = "1.3.2" hex = "0.4.2" itertools = "0.9.0" lazy_static = "1.4.0" diff --git a/dhall/src/ctxt.rs b/dhall/src/ctxt.rs new file mode 100644 index 0000000..1d97232 --- /dev/null +++ b/dhall/src/ctxt.rs @@ -0,0 +1,109 @@ +use elsa::vec::FrozenVec; +use once_cell::sync::OnceCell; + +use crate::semantics::{Import, ImportLocation}; +use crate::syntax::Span; +use crate::Typed; + +#[derive(Debug, Copy, Clone, PartialEq, Eq, Hash)] +pub struct ImportId(usize); +#[derive(Debug, Copy, Clone, PartialEq, Eq, Hash)] +pub struct ImportResultId(usize); + +struct StoredImport { + base_location: ImportLocation, + import: Import, + span: Span, + result: OnceCell, +} + +#[derive(Default)] +struct CtxtS { + imports: FrozenVec>, + import_results: FrozenVec>, +} + +/// Context for the dhall compiler. Stores various global maps. +#[derive(Copy, Clone)] +pub struct Ctxt<'cx>(&'cx CtxtS); + +impl Ctxt<'_> { + pub fn with_new(f: impl for<'cx> FnOnce(Ctxt<'cx>) -> T) -> T { + let cx = CtxtS::default(); + let cx = Ctxt(&cx); + f(cx) + } +} +impl<'cx> Ctxt<'cx> { + fn get_stored_import(self, import: ImportId) -> &'cx StoredImport { + self.0.imports.get(import.0).unwrap() + } + pub fn get_import_result(self, id: ImportResultId) -> &'cx Typed { + &self.0.import_results.get(id.0).unwrap() + } + + /// Store an import and the location relative to which it must be resolved. + pub fn push_import( + self, + base_location: ImportLocation, + import: Import, + span: Span, + ) -> ImportId { + let stored = StoredImport { + base_location, + import, + span, + result: OnceCell::new(), + }; + let id = self.0.imports.len(); + self.0.imports.push(Box::new(stored)); + ImportId(id) + } + /// Store the result of fetching an import. + pub fn push_import_result(self, res: Typed) -> ImportResultId { + let id = self.0.import_results.len(); + self.0.import_results.push(Box::new(res)); + ImportResultId(id) + } + + pub fn get_import(self, import: ImportId) -> &'cx Import { + &self.get_stored_import(import).import + } + pub fn get_import_base_location( + self, + import: ImportId, + ) -> &'cx ImportLocation { + &self.get_stored_import(import).base_location + } + pub fn get_import_span(self, import: ImportId) -> Span { + self.get_stored_import(import).span.clone() + } + /// Get the result of fetching this import. Returns `None` if the result has not yet been + /// fetched. + pub fn get_result_of_import(self, import: ImportId) -> Option<&'cx Typed> { + let res = self.get_resultid_of_import(import)?; + Some(self.get_import_result(res)) + } + /// Get the id of the result of fetching this import. Returns `None` if the result has not yet + /// been fetched. + pub fn get_resultid_of_import( + self, + import: ImportId, + ) -> Option { + self.get_stored_import(import).result.get().copied() + } + /// Store the result of fetching this import. + pub fn set_result_of_import( + self, + import: ImportId, + res: Typed, + ) -> ImportResultId { + let res = self.push_import_result(res); + self.set_resultid_of_import(import, res); + res + } + /// Store the result of fetching this import. + pub fn set_resultid_of_import(self, import: ImportId, res: ImportResultId) { + let _ = self.get_stored_import(import).result.set(res); + } +} diff --git a/dhall/src/lib.rs b/dhall/src/lib.rs index 6747eff..d079e92 100644 --- a/dhall/src/lib.rs +++ b/dhall/src/lib.rs @@ -9,6 +9,7 @@ )] pub mod builtins; +pub mod ctxt; pub mod error; pub mod operations; pub mod semantics; @@ -26,6 +27,8 @@ use crate::semantics::resolve::ImportLocation; use crate::semantics::{typecheck, typecheck_with, Hir, Nir, Tir, Type}; use crate::syntax::Expr; +pub use ctxt::{Ctxt, ImportId, ImportResultId}; + #[derive(Debug, Clone)] pub struct Parsed(Expr, ImportLocation); diff --git a/dhall/src/semantics/resolve/env.rs b/dhall/src/semantics/resolve/env.rs index 29dd16b..82f21e8 100644 --- a/dhall/src/semantics/resolve/env.rs +++ b/dhall/src/semantics/resolve/env.rs @@ -3,7 +3,7 @@ use std::collections::HashMap; use crate::error::{Error, ImportError}; use crate::semantics::{AlphaVar, Cache, ImportLocation, VarEnv}; use crate::syntax::{Hash, Label, V}; -use crate::Typed; +use crate::{Ctxt, ImportResultId, Typed}; /// Environment for resolving names. #[derive(Debug, Clone, Default)] @@ -11,14 +11,13 @@ pub struct NameEnv { names: Vec