Various progress, doesnt compile

Added prelude, made lambdas a single-token prefix like NS, made progress on implementations, removed const line type
This commit is contained in:
2025-07-31 00:30:41 +02:00
parent 19f2c6426a
commit 769c6cfc9f
31 changed files with 450 additions and 250 deletions

View File

@@ -23,7 +23,7 @@ use orchid_base::name::Sym;
use crate::api;
use crate::atom::{
AtomCard, AtomCtx, AtomDynfo, AtomFactory, Atomic, AtomicFeaturesImpl, AtomicVariant, MethodSet,
MethodSetBuilder, err_not_callable, err_not_command, get_info,
MethodSetBuilder, TypAtom, err_not_callable, err_not_command, get_info,
};
use crate::expr::Expr;
use crate::gen_expr::{GExpr, bot};
@@ -68,6 +68,7 @@ impl Deref for AtomReadGuard<'_> {
fn deref(&self) -> &Self::Target { &**self.guard.get(&self.id).unwrap() }
}
/// Remove an atom from the store
pub(crate) async fn take_atom(id: api::AtomId, ctx: &SysCtx) -> Box<dyn DynOwnedAtom> {
let mut g = ctx.get_or_default::<ObjStore>().objects.write().await;
g.remove(&id).unwrap_or_else(|| panic!("Received invalid atom ID: {}", id.0))
@@ -313,3 +314,11 @@ struct ObjStore {
objects: RwLock<MemoMap<api::AtomId, Box<dyn DynOwnedAtom>>>,
}
impl SysCtxEntry for ObjStore {}
pub async fn get_own_instance<A: OwnedAtom>(typ: TypAtom<A>) -> A {
let ctx = typ.data.ctx();
let g = ctx.get_or_default::<ObjStore>().objects.read().await;
let dyn_atom = (g.get(&typ.data.atom.drop.expect("Owned atoms always have a drop ID")))
.expect("Atom ID invalid; atom type probably not owned by this crate");
dyn_atom.as_any_ref().downcast_ref().cloned().expect("The ID should imply a type as well")
}

View File

@@ -1,5 +1,6 @@
use std::future::Future;
use never::Never;
use orchid_base::error::{OrcErr, OrcRes, mk_err};
use orchid_base::interner::Interner;
use orchid_base::location::Pos;
@@ -7,7 +8,7 @@ use orchid_base::location::Pos;
use crate::atom::{AtomicFeatures, ToAtom, TypAtom};
use crate::expr::Expr;
use crate::gen_expr::{GExpr, atom, bot};
use crate::system::downcast_atom;
use crate::system::{SysCtx, downcast_atom};
pub trait TryFromExpr: Sized {
fn try_from_expr(expr: Expr) -> impl Future<Output = OrcRes<Self>>;
@@ -43,6 +44,10 @@ impl<A: AtomicFeatures> TryFromExpr for TypAtom<A> {
}
}
impl TryFromExpr for SysCtx {
async fn try_from_expr(expr: Expr) -> OrcRes<Self> { Ok(expr.ctx()) }
}
pub trait ToExpr {
fn to_expr(self) -> GExpr;
}
@@ -66,3 +71,7 @@ impl<T: ToExpr> ToExpr for OrcRes<T> {
impl<A: ToAtom> ToExpr for A {
fn to_expr(self) -> GExpr { atom(self) }
}
impl ToExpr for Never {
fn to_expr(self) -> GExpr { match self {} }
}

View File

@@ -17,6 +17,7 @@ use orchid_api_traits::{Decode, UnderRoot, enc_vec};
use orchid_base::builtin::{ExtInit, ExtPort, Spawner};
use orchid_base::char_filter::{char_filter_match, char_filter_union, mk_char_filter};
use orchid_base::clone;
use orchid_base::error::Reporter;
use orchid_base::interner::{Interner, Tok};
use orchid_base::logging::Logger;
use orchid_base::name::Sym;
@@ -189,10 +190,13 @@ pub fn extension_init(
})
.collect()
.await;
let prelude =
cted.inst().dyn_prelude(&i).await.iter().map(|sym| sym.to_api()).collect();
let record = SystemRecord { ctx, lazy_members: lazy_mems.into_inner() };
let systems = systems_weak.upgrade().expect("System constructed during shutdown");
systems.lock().await.insert(new_sys.id, record);
let response = api::NewSystemResponse { lex_filter, const_root, line_types: vec![] };
let response =
api::NewSystemResponse { lex_filter, const_root, line_types: vec![], prelude };
hand.handle(&new_sys, &response).await
},
api::HostExtReq::GetMember(get_tree @ api::GetMember(sys_id, tree_id)) => {
@@ -262,8 +266,10 @@ pub fn extension_init(
let parser =
parsers.iter().find(|p| p.line_head() == **name).expect("No parser candidate");
let module = Sym::from_api(*module, ctx.i()).await;
let pctx = ParsCtx::new(ctx.clone(), module);
let o_line = match parser.parse(pctx, *exported, comments, tail).await {
let reporter = Reporter::new();
let pctx = ParsCtx::new(ctx.clone(), module, &reporter);
let parse_res = parser.parse(pctx, *exported, comments, tail).await;
let o_line = match reporter.merge(parse_res) {
Err(e) => Err(e.to_api()),
Ok(t) => Ok(linev_into_api(t, ctx.clone(), &hand).await),
};

View File

@@ -4,12 +4,12 @@ use futures::FutureExt;
use futures::future::{LocalBoxFuture, join_all};
use itertools::Itertools;
use orchid_api::ResolveNames;
use orchid_base::error::OrcRes;
use orchid_base::error::{OrcRes, Reporter};
use orchid_base::id_store::IdStore;
use orchid_base::interner::Tok;
use orchid_base::interner::{Interner, Tok};
use orchid_base::location::SrcRange;
use orchid_base::name::Sym;
use orchid_base::parse::{Comment, Snippet};
use orchid_base::parse::{Comment, ParseCtx, Snippet};
use orchid_base::reqnot::{ReqHandlish, Requester};
use orchid_base::tree::ttv_into_api;
@@ -61,12 +61,19 @@ pub struct ParsCtx<'a> {
_parse: PhantomData<&'a mut ()>,
ctx: SysCtx,
module: Sym,
reporter: &'a Reporter,
}
impl ParsCtx<'_> {
pub(crate) fn new(ctx: SysCtx, module: Sym) -> Self { Self { _parse: PhantomData, ctx, module } }
impl<'a> ParsCtx<'a> {
pub(crate) fn new(ctx: SysCtx, module: Sym, reporter: &'a Reporter) -> Self {
Self { _parse: PhantomData, ctx, module, reporter }
}
pub fn ctx(&self) -> &SysCtx { &self.ctx }
pub fn module(&self) -> Sym { self.module.clone() }
}
impl ParseCtx for ParsCtx<'_> {
fn i(&self) -> &Interner { self.ctx.i() }
fn reporter(&self) -> &Reporter { self.reporter }
}
type BoxConstCallback = Box<dyn FnOnce(ConstCtx) -> LocalBoxFuture<'static, GExpr>>;
@@ -94,8 +101,10 @@ impl ParsedLine {
ParsedMemKind::Const(cb) => api::ParsedMemberKind::Constant(api::ParsedConstId(
ctx.get_or_default::<ParsedConstCtxEntry>().consts.add(cb).id(),
)),
ParsedMemKind::Mod(plv) =>
api::ParsedMemberKind::Module(linev_into_api(plv, ctx, hand).boxed_local().await),
ParsedMemKind::Mod { lines, use_prelude } => api::ParsedMemberKind::Module {
lines: linev_into_api(lines, ctx, hand).boxed_local().await,
use_prelude,
},
},
}),
ParsedLineKind::Rec(tv) =>
@@ -119,20 +128,26 @@ pub enum ParsedLineKind {
}
pub struct ParsedMem {
name: Tok<String>,
exported: bool,
kind: ParsedMemKind,
pub name: Tok<String>,
pub exported: bool,
pub kind: ParsedMemKind,
}
pub enum ParsedMemKind {
Const(BoxConstCallback),
Mod(Vec<ParsedLine>),
Mod { lines: Vec<ParsedLine>, use_prelude: bool },
}
impl ParsedMemKind {
pub fn cnst<F: AsyncFnOnce(ConstCtx) -> GExpr + 'static>(f: F) -> Self {
Self::Const(Box::new(|ctx| Box::pin(f(ctx))))
}
pub fn module(lines: impl IntoIterator<Item = ParsedLine>) -> Self {
Self::Mod { lines: lines.into_iter().collect(), use_prelude: true }
}
pub fn clean_module(lines: impl IntoIterator<Item = ParsedLine>) -> Self {
Self::Mod { lines: lines.into_iter().collect(), use_prelude: false }
}
}
/* TODO: how the macro runner uses the multi-stage loader

View File

@@ -13,6 +13,7 @@ use orchid_base::boxed_iter::BoxedIter;
use orchid_base::builtin::Spawner;
use orchid_base::interner::Interner;
use orchid_base::logging::Logger;
use orchid_base::name::Sym;
use orchid_base::reqnot::{Receipt, ReqNot};
use crate::api;
@@ -81,6 +82,7 @@ impl<T: SystemCard> DynSystemCard for T {
/// System as defined by author
pub trait System: Send + Sync + SystemCard + 'static {
fn prelude(i: &Interner) -> impl Future<Output = Vec<Sym>>;
fn env() -> Vec<GenMember>;
fn lexers() -> Vec<LexerObj>;
fn parsers() -> Vec<ParserObj>;
@@ -88,6 +90,7 @@ pub trait System: Send + Sync + SystemCard + 'static {
}
pub trait DynSystem: Send + Sync + DynSystemCard + 'static {
fn dyn_prelude<'a>(&'a self, i: &'a Interner) -> LocalBoxFuture<'a, Vec<Sym>>;
fn dyn_env(&self) -> Vec<GenMember>;
fn dyn_lexers(&self) -> Vec<LexerObj>;
fn dyn_parsers(&self) -> Vec<ParserObj>;
@@ -96,6 +99,9 @@ pub trait DynSystem: Send + Sync + DynSystemCard + 'static {
}
impl<T: System> DynSystem for T {
fn dyn_prelude<'a>(&'a self, i: &'a Interner) -> LocalBoxFuture<'a, Vec<Sym>> {
Box::pin(Self::prelude(i))
}
fn dyn_env(&self) -> Vec<GenMember> { Self::env() }
fn dyn_lexers(&self) -> Vec<LexerObj> { Self::lexers() }
fn dyn_parsers(&self) -> Vec<ParserObj> { Self::parsers() }
@@ -129,22 +135,6 @@ where A: AtomicFeatures {
Ok(TypAtom { value, data: foreign })
}
// #[derive(Clone)]
// pub struct SysCtx {
// pub reqnot: ReqNot<api::ExtMsgSet>,
// pub spawner: Spawner,
// pub id: api::SysId,
// pub cted: CtedObj,
// pub logger: Logger,
// pub obj_store: ObjStore,
// pub i: Rc<Interner>,
// }
// impl fmt::Debug for SysCtx {
// fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
// write!(f, "SysCtx({:?})", self.id)
// }
// }
#[derive(Clone)]
pub struct SysCtx(Rc<MemoMap<TypeId, Box<dyn Any>>>);
impl SysCtx {