Unify u32-based identifiers into common code
Create a new type Id<T> paramaterized by whatever specific class of IDs is relevant to a domain; create stores and macros to support this; and repace the existing Id types.
This commit is contained in:
parent
a3463f5519
commit
d65233240a
@ -4,4 +4,5 @@ use_small_heuristics = "max"
|
|||||||
imports_indent = "block"
|
imports_indent = "block"
|
||||||
imports_granularity = "crate"
|
imports_granularity = "crate"
|
||||||
group_imports = "stdexternalcrate"
|
group_imports = "stdexternalcrate"
|
||||||
|
match_arm_blocks = false
|
||||||
|
where_single_line = true
|
||||||
|
@ -2,7 +2,6 @@
|
|||||||
#![allow(clippy::enum_variant_names)]
|
#![allow(clippy::enum_variant_names)]
|
||||||
|
|
||||||
use std::rc::Rc;
|
use std::rc::Rc;
|
||||||
use std::fmt;
|
|
||||||
use std::convert::{AsRef, From};
|
use std::convert::{AsRef, From};
|
||||||
|
|
||||||
mod visitor;
|
mod visitor;
|
||||||
@ -13,41 +12,19 @@ pub use visitor::*;
|
|||||||
|
|
||||||
use crate::derivative::Derivative;
|
use crate::derivative::Derivative;
|
||||||
use crate::tokenizing::Location;
|
use crate::tokenizing::Location;
|
||||||
|
use crate::identifier::{Id, define_id_kind};
|
||||||
|
|
||||||
/// An abstract identifier for an AST node. Note that
|
define_id_kind!(ASTItem);
|
||||||
/// the u32 index limits the size of an AST to 2^32 nodes.
|
|
||||||
#[derive(Debug, PartialEq, Eq, Hash, Clone, Default)]
|
|
||||||
pub struct ItemId {
|
|
||||||
pub idx: u32,
|
|
||||||
}
|
|
||||||
|
|
||||||
impl ItemId {
|
/*
|
||||||
fn new(n: u32) -> ItemId {
|
#[derive(Debug, Copy, Clone, PartialEq, Eq, Hash, Default)]
|
||||||
ItemId { idx: n }
|
pub struct ASTItem;
|
||||||
}
|
impl IdKind for ASTItem {
|
||||||
|
fn tag() -> &'static str { "ASTItem" }
|
||||||
}
|
}
|
||||||
|
*/
|
||||||
|
|
||||||
impl fmt::Display for ItemId {
|
pub type ItemId = Id<ASTItem>;
|
||||||
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
|
|
||||||
write!(f, "ItemId:{}", self.idx)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
pub struct ItemIdStore {
|
|
||||||
last_idx: u32
|
|
||||||
}
|
|
||||||
|
|
||||||
impl ItemIdStore {
|
|
||||||
pub fn new() -> ItemIdStore {
|
|
||||||
ItemIdStore { last_idx: 0 }
|
|
||||||
}
|
|
||||||
|
|
||||||
pub fn fresh(&mut self) -> ItemId {
|
|
||||||
let idx = self.last_idx;
|
|
||||||
self.last_idx += 1;
|
|
||||||
ItemId::new(idx)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
#[derive(Derivative, Debug)]
|
#[derive(Derivative, Debug)]
|
||||||
#[derivative(PartialEq)]
|
#[derivative(PartialEq)]
|
||||||
|
74
schala-lang/language/src/identifier.rs
Normal file
74
schala-lang/language/src/identifier.rs
Normal file
@ -0,0 +1,74 @@
|
|||||||
|
use std::{
|
||||||
|
fmt::{self, Debug},
|
||||||
|
hash::Hash,
|
||||||
|
marker::PhantomData,
|
||||||
|
};
|
||||||
|
|
||||||
|
pub trait IdKind: Debug + Copy + Clone + Hash + PartialEq + Eq + Default {
|
||||||
|
fn tag() -> &'static str;
|
||||||
|
}
|
||||||
|
|
||||||
|
/// A generalized abstract identifier type of up to 2^32-1 entries.
|
||||||
|
#[derive(Debug, Copy, Clone, Hash, PartialEq, Eq, Default)]
|
||||||
|
pub struct Id<T>
|
||||||
|
where T: IdKind
|
||||||
|
{
|
||||||
|
idx: u32,
|
||||||
|
t: PhantomData<T>,
|
||||||
|
}
|
||||||
|
|
||||||
|
impl<T> Id<T>
|
||||||
|
where T: IdKind
|
||||||
|
{
|
||||||
|
fn new(n: u32) -> Self {
|
||||||
|
Self { idx: n, t: PhantomData }
|
||||||
|
}
|
||||||
|
|
||||||
|
#[allow(dead_code)]
|
||||||
|
pub fn as_u32(&self) -> u32 {
|
||||||
|
self.idx
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl<T> fmt::Display for Id<T>
|
||||||
|
where T: IdKind
|
||||||
|
{
|
||||||
|
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
|
||||||
|
write!(f, "{}:{}", self.idx, T::tag())
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
pub struct IdStore<T>
|
||||||
|
where T: IdKind
|
||||||
|
{
|
||||||
|
last_idx: u32,
|
||||||
|
t: PhantomData<T>,
|
||||||
|
}
|
||||||
|
|
||||||
|
impl<T> IdStore<T>
|
||||||
|
where T: IdKind
|
||||||
|
{
|
||||||
|
pub fn new() -> Self {
|
||||||
|
Self { last_idx: 0, t: PhantomData }
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn fresh(&mut self) -> Id<T> {
|
||||||
|
let idx = self.last_idx;
|
||||||
|
self.last_idx += 1;
|
||||||
|
Id::new(idx)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
macro_rules! define_id_kind {
|
||||||
|
($name:ident) => {
|
||||||
|
#[derive(Debug, Copy, Clone, Hash, PartialEq, Eq, Default)]
|
||||||
|
pub struct $name;
|
||||||
|
impl crate::identifier::IdKind for $name {
|
||||||
|
fn tag() -> &'static str {
|
||||||
|
stringify!($name)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
pub(crate) use define_id_kind;
|
@ -23,10 +23,10 @@ mod tokenizing;
|
|||||||
mod symbol_table;
|
mod symbol_table;
|
||||||
mod builtin;
|
mod builtin;
|
||||||
mod error;
|
mod error;
|
||||||
//mod eval;
|
|
||||||
//mod reduced_ast;
|
|
||||||
mod reduced_ir;
|
mod reduced_ir;
|
||||||
mod tree_walk_eval;
|
mod tree_walk_eval;
|
||||||
|
#[macro_use]
|
||||||
|
mod identifier;
|
||||||
|
|
||||||
mod schala;
|
mod schala;
|
||||||
|
|
||||||
|
@ -170,6 +170,7 @@ use crate::tokenizing::TokenKind::*;
|
|||||||
use crate::tokenizing::Location;
|
use crate::tokenizing::Location;
|
||||||
|
|
||||||
use crate::ast::*;
|
use crate::ast::*;
|
||||||
|
use crate::identifier::IdStore;
|
||||||
|
|
||||||
/// Represents a parsing error
|
/// Represents a parsing error
|
||||||
#[derive(Debug)]
|
#[derive(Debug)]
|
||||||
@ -201,7 +202,7 @@ pub struct Parser {
|
|||||||
parse_record: Vec<ParseRecord>,
|
parse_record: Vec<ParseRecord>,
|
||||||
parse_level: u32,
|
parse_level: u32,
|
||||||
restrictions: ParserRestrictions,
|
restrictions: ParserRestrictions,
|
||||||
id_store: ItemIdStore,
|
id_store: IdStore<ASTItem>,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -252,7 +253,7 @@ impl Parser {
|
|||||||
parse_record: vec![],
|
parse_record: vec![],
|
||||||
parse_level: 0,
|
parse_level: 0,
|
||||||
restrictions: ParserRestrictions { no_struct_literal: false },
|
restrictions: ParserRestrictions { no_struct_literal: false },
|
||||||
id_store: ItemIdStore::new(),
|
id_store: IdStore::new(),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -14,42 +14,10 @@ mod resolver;
|
|||||||
mod symbol_trie;
|
mod symbol_trie;
|
||||||
use symbol_trie::SymbolTrie;
|
use symbol_trie::SymbolTrie;
|
||||||
mod test;
|
mod test;
|
||||||
|
use crate::identifier::{Id, IdStore, define_id_kind};
|
||||||
|
|
||||||
|
define_id_kind!(DefItem);
|
||||||
//TODO parameterize different types of ID
|
pub type DefId = Id<DefItem>;
|
||||||
/// ID used for definitions
|
|
||||||
#[derive(Debug, PartialEq, Eq, Hash, Clone, Default)]
|
|
||||||
pub struct DefId {
|
|
||||||
idx: u32,
|
|
||||||
}
|
|
||||||
|
|
||||||
impl DefId {
|
|
||||||
pub fn as_u32(&self) -> u32 {
|
|
||||||
self.idx
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
impl fmt::Display for DefId {
|
|
||||||
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
|
|
||||||
write!(f, "DefId:{}", self.idx)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
pub struct DefIdStore {
|
|
||||||
last_idx: u32
|
|
||||||
}
|
|
||||||
|
|
||||||
impl DefIdStore {
|
|
||||||
pub fn new() -> Self {
|
|
||||||
Self { last_idx: 0 }
|
|
||||||
}
|
|
||||||
|
|
||||||
pub fn fresh(&mut self) -> DefId {
|
|
||||||
let idx = self.last_idx;
|
|
||||||
self.last_idx += 1;
|
|
||||||
DefId { idx }
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/// Fully-qualified symbol name
|
/// Fully-qualified symbol name
|
||||||
#[derive(Debug, Clone, Eq, PartialEq, Hash, PartialOrd, Ord)]
|
#[derive(Debug, Clone, Eq, PartialEq, Hash, PartialOrd, Ord)]
|
||||||
@ -170,7 +138,7 @@ impl<K> NameTable<K> {
|
|||||||
//cf. p. 150 or so of Language Implementation Patterns
|
//cf. p. 150 or so of Language Implementation Patterns
|
||||||
pub struct SymbolTable {
|
pub struct SymbolTable {
|
||||||
|
|
||||||
def_id_store: DefIdStore,
|
def_id_store: IdStore<DefItem>,
|
||||||
|
|
||||||
/// Used for import resolution.
|
/// Used for import resolution.
|
||||||
symbol_trie: SymbolTrie,
|
symbol_trie: SymbolTrie,
|
||||||
@ -190,7 +158,7 @@ pub struct SymbolTable {
|
|||||||
impl SymbolTable {
|
impl SymbolTable {
|
||||||
pub fn new() -> SymbolTable {
|
pub fn new() -> SymbolTable {
|
||||||
SymbolTable {
|
SymbolTable {
|
||||||
def_id_store: DefIdStore::new(),
|
def_id_store: IdStore::new(),
|
||||||
symbol_trie: SymbolTrie::new(),
|
symbol_trie: SymbolTrie::new(),
|
||||||
fq_names: NameTable::new(),
|
fq_names: NameTable::new(),
|
||||||
types: NameTable::new(),
|
types: NameTable::new(),
|
||||||
|
Loading…
Reference in New Issue
Block a user