Simplify lifetimes.
This commit is contained in:
parent
ed568a9395
commit
ade290da7e
@ -21,6 +21,7 @@ Breaking changes
|
|||||||
* `Module::update_fn_metadata` input parameter is changed.
|
* `Module::update_fn_metadata` input parameter is changed.
|
||||||
* Function keywords (e.g. `type_of`, `eval`, `Fn`) can no longer be overloaded. It is more trouble than worth. To disable these keywords, use `Engine::disable_symbol`.
|
* Function keywords (e.g. `type_of`, `eval`, `Fn`) can no longer be overloaded. It is more trouble than worth. To disable these keywords, use `Engine::disable_symbol`.
|
||||||
* `is_def_var` and `is_def_fn` are now reserved keywords.
|
* `is_def_var` and `is_def_fn` are now reserved keywords.
|
||||||
|
* `Engine::id` field is removed.
|
||||||
|
|
||||||
Enhancements
|
Enhancements
|
||||||
------------
|
------------
|
||||||
|
@ -525,18 +525,6 @@ impl State {
|
|||||||
pub fn is_global(&self) -> bool {
|
pub fn is_global(&self) -> bool {
|
||||||
self.scope_level == 0
|
self.scope_level == 0
|
||||||
}
|
}
|
||||||
/// Get the current functions resolution cache.
|
|
||||||
pub fn fn_resolution_cache(
|
|
||||||
&self,
|
|
||||||
) -> Option<
|
|
||||||
&HashMap<
|
|
||||||
NonZeroU64,
|
|
||||||
Option<(CallableFunction, Option<ImmutableString>)>,
|
|
||||||
StraightHasherBuilder,
|
|
||||||
>,
|
|
||||||
> {
|
|
||||||
self.fn_resolution_caches.last()
|
|
||||||
}
|
|
||||||
/// Get a mutable reference to the current functions resolution cache.
|
/// Get a mutable reference to the current functions resolution cache.
|
||||||
pub fn fn_resolution_cache_mut(
|
pub fn fn_resolution_cache_mut(
|
||||||
&mut self,
|
&mut self,
|
||||||
@ -617,17 +605,17 @@ pub struct Limits {
|
|||||||
|
|
||||||
/// Context of a script evaluation process.
|
/// Context of a script evaluation process.
|
||||||
#[derive(Debug)]
|
#[derive(Debug)]
|
||||||
pub struct EvalContext<'e, 'x, 'px, 'a, 's, 'm, 't, 'pt> {
|
pub struct EvalContext<'a, 'x, 'px, 'm, 's, 't, 'pt> {
|
||||||
pub(crate) engine: &'e Engine,
|
pub(crate) engine: &'a Engine,
|
||||||
pub(crate) scope: &'x mut Scope<'px>,
|
pub(crate) scope: &'x mut Scope<'px>,
|
||||||
pub(crate) mods: &'a mut Imports,
|
pub(crate) mods: &'m mut Imports,
|
||||||
pub(crate) state: &'s mut State,
|
pub(crate) state: &'s mut State,
|
||||||
pub(crate) lib: &'m [&'m Module],
|
pub(crate) lib: &'a [&'a Module],
|
||||||
pub(crate) this_ptr: &'t mut Option<&'pt mut Dynamic>,
|
pub(crate) this_ptr: &'t mut Option<&'pt mut Dynamic>,
|
||||||
pub(crate) level: usize,
|
pub(crate) level: usize,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<'e, 'x, 'px, 'a, 's, 'm, 't, 'pt> EvalContext<'e, 'x, 'px, 'a, 's, 'm, 't, 'pt> {
|
impl<'x, 'px> EvalContext<'_, 'x, 'px, '_, '_, '_, '_> {
|
||||||
/// The current [`Engine`].
|
/// The current [`Engine`].
|
||||||
#[inline(always)]
|
#[inline(always)]
|
||||||
pub fn engine(&self) -> &Engine {
|
pub fn engine(&self) -> &Engine {
|
||||||
@ -710,9 +698,6 @@ impl<'e, 'x, 'px, 'a, 's, 'm, 't, 'pt> EvalContext<'e, 'x, 'px, 'a, 's, 'm, 't,
|
|||||||
/// # }
|
/// # }
|
||||||
/// ```
|
/// ```
|
||||||
pub struct Engine {
|
pub struct Engine {
|
||||||
/// A unique ID identifying this scripting [`Engine`].
|
|
||||||
pub id: String,
|
|
||||||
|
|
||||||
/// A module containing all functions directly loaded into the Engine.
|
/// A module containing all functions directly loaded into the Engine.
|
||||||
pub(crate) global_namespace: Module,
|
pub(crate) global_namespace: Module,
|
||||||
/// A collection of all modules loaded into the global namespace of the Engine.
|
/// A collection of all modules loaded into the global namespace of the Engine.
|
||||||
@ -757,12 +742,8 @@ pub struct Engine {
|
|||||||
impl fmt::Debug for Engine {
|
impl fmt::Debug for Engine {
|
||||||
#[inline(always)]
|
#[inline(always)]
|
||||||
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
|
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
|
||||||
if !self.id.is_empty() {
|
|
||||||
write!(f, "Engine({})", self.id)
|
|
||||||
} else {
|
|
||||||
f.write_str("Engine")
|
f.write_str("Engine")
|
||||||
}
|
}
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
impl Default for Engine {
|
impl Default for Engine {
|
||||||
@ -819,8 +800,6 @@ impl Engine {
|
|||||||
pub fn new() -> Self {
|
pub fn new() -> Self {
|
||||||
// Create the new scripting Engine
|
// Create the new scripting Engine
|
||||||
let mut engine = Self {
|
let mut engine = Self {
|
||||||
id: Default::default(),
|
|
||||||
|
|
||||||
global_namespace: Default::default(),
|
global_namespace: Default::default(),
|
||||||
global_modules: Default::default(),
|
global_modules: Default::default(),
|
||||||
global_sub_modules: Default::default(),
|
global_sub_modules: Default::default(),
|
||||||
@ -886,8 +865,6 @@ impl Engine {
|
|||||||
#[inline]
|
#[inline]
|
||||||
pub fn new_raw() -> Self {
|
pub fn new_raw() -> Self {
|
||||||
Self {
|
Self {
|
||||||
id: Default::default(),
|
|
||||||
|
|
||||||
global_namespace: Default::default(),
|
global_namespace: Default::default(),
|
||||||
global_modules: Default::default(),
|
global_modules: Default::default(),
|
||||||
global_sub_modules: Default::default(),
|
global_sub_modules: Default::default(),
|
||||||
@ -934,14 +911,13 @@ impl Engine {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/// Search for a module within an imports stack.
|
/// Search for a module within an imports stack.
|
||||||
/// [`Position`] in [`EvalAltResult`] is [`NONE`][Position::NONE] and must be set afterwards.
|
pub(crate) fn search_imports(
|
||||||
pub fn search_imports(
|
|
||||||
&self,
|
&self,
|
||||||
mods: &Imports,
|
mods: &Imports,
|
||||||
state: &mut State,
|
state: &mut State,
|
||||||
namespace: &NamespaceRef,
|
namespace: &NamespaceRef,
|
||||||
) -> Result<Shared<Module>, Box<EvalAltResult>> {
|
) -> Option<Shared<Module>> {
|
||||||
let Ident { name: root, pos } = &namespace[0];
|
let root = &namespace[0].name;
|
||||||
|
|
||||||
// Qualified - check if the root module is directly indexed
|
// Qualified - check if the root module is directly indexed
|
||||||
let index = if state.always_search {
|
let index = if state.always_search {
|
||||||
@ -950,15 +926,14 @@ impl Engine {
|
|||||||
namespace.index()
|
namespace.index()
|
||||||
};
|
};
|
||||||
|
|
||||||
Ok(if let Some(index) = index {
|
if let Some(index) = index {
|
||||||
let offset = mods.len() - index.get();
|
let offset = mods.len() - index.get();
|
||||||
mods.get(offset).expect("invalid index in Imports")
|
Some(mods.get(offset).expect("invalid index in Imports"))
|
||||||
} else {
|
} else {
|
||||||
mods.find(root)
|
mods.find(root)
|
||||||
.map(|n| mods.get(n).expect("invalid index in Imports"))
|
.map(|n| mods.get(n).expect("invalid index in Imports"))
|
||||||
.or_else(|| self.global_sub_modules.get(root).cloned())
|
.or_else(|| self.global_sub_modules.get(root).cloned())
|
||||||
.ok_or_else(|| EvalAltResult::ErrorModuleNotFound(root.to_string(), *pos))?
|
}
|
||||||
})
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Search for a variable within the scope or within imports,
|
/// Search for a variable within the scope or within imports,
|
||||||
@ -976,7 +951,12 @@ impl Engine {
|
|||||||
Expr::Variable(v) => match v.as_ref() {
|
Expr::Variable(v) => match v.as_ref() {
|
||||||
// Qualified variable
|
// Qualified variable
|
||||||
(_, Some((hash_var, modules)), Ident { name, pos }) => {
|
(_, Some((hash_var, modules)), Ident { name, pos }) => {
|
||||||
let module = self.search_imports(mods, state, modules)?;
|
let module = self.search_imports(mods, state, modules).ok_or_else(|| {
|
||||||
|
EvalAltResult::ErrorModuleNotFound(
|
||||||
|
modules[0].name.to_string(),
|
||||||
|
modules[0].pos,
|
||||||
|
)
|
||||||
|
})?;
|
||||||
let target = module.get_qualified_var(*hash_var).map_err(|mut err| {
|
let target = module.get_qualified_var(*hash_var).map_err(|mut err| {
|
||||||
match *err {
|
match *err {
|
||||||
EvalAltResult::ErrorVariableNotFound(ref mut err_name, _) => {
|
EvalAltResult::ErrorVariableNotFound(ref mut err_name, _) => {
|
||||||
@ -1068,7 +1048,7 @@ impl Engine {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/// Chain-evaluate a dot/index chain.
|
/// Chain-evaluate a dot/index chain.
|
||||||
/// [`Position`] in [`EvalAltResult`] is [`None`][Position::None] and must be set afterwards.
|
/// [`Position`] in [`EvalAltResult`] is [`NONE`][Position::NONE] and must be set afterwards.
|
||||||
#[cfg(any(not(feature = "no_index"), not(feature = "no_object")))]
|
#[cfg(any(not(feature = "no_index"), not(feature = "no_object")))]
|
||||||
fn eval_dot_index_chain_helper(
|
fn eval_dot_index_chain_helper(
|
||||||
&self,
|
&self,
|
||||||
|
@ -1028,7 +1028,7 @@ impl Engine {
|
|||||||
scripts: &[&str],
|
scripts: &[&str],
|
||||||
optimization_level: OptimizationLevel,
|
optimization_level: OptimizationLevel,
|
||||||
) -> Result<AST, ParseError> {
|
) -> Result<AST, ParseError> {
|
||||||
let stream = self.lex(scripts);
|
let stream = self.lex_raw(scripts, None);
|
||||||
self.parse(&mut stream.peekable(), scope, optimization_level)
|
self.parse(&mut stream.peekable(), scope, optimization_level)
|
||||||
}
|
}
|
||||||
/// Read the contents of a file into a string.
|
/// Read the contents of a file into a string.
|
||||||
@ -1190,9 +1190,9 @@ impl Engine {
|
|||||||
.into());
|
.into());
|
||||||
};
|
};
|
||||||
|
|
||||||
let stream = self.lex_with_map(
|
let stream = self.lex_raw(
|
||||||
&scripts,
|
&scripts,
|
||||||
if has_null {
|
Some(if has_null {
|
||||||
|token| match token {
|
|token| match token {
|
||||||
// If `null` is present, make sure `null` is treated as a variable
|
// If `null` is present, make sure `null` is treated as a variable
|
||||||
Token::Reserved(s) if s == "null" => Token::Identifier(s),
|
Token::Reserved(s) if s == "null" => Token::Identifier(s),
|
||||||
@ -1200,7 +1200,7 @@ impl Engine {
|
|||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
|t| t
|
|t| t
|
||||||
},
|
}),
|
||||||
);
|
);
|
||||||
|
|
||||||
let ast =
|
let ast =
|
||||||
@ -1283,7 +1283,7 @@ impl Engine {
|
|||||||
script: &str,
|
script: &str,
|
||||||
) -> Result<AST, ParseError> {
|
) -> Result<AST, ParseError> {
|
||||||
let scripts = [script];
|
let scripts = [script];
|
||||||
let stream = self.lex(&scripts);
|
let stream = self.lex_raw(&scripts, None);
|
||||||
|
|
||||||
let mut peekable = stream.peekable();
|
let mut peekable = stream.peekable();
|
||||||
self.parse_global_expr(&mut peekable, scope, self.optimization_level)
|
self.parse_global_expr(&mut peekable, scope, self.optimization_level)
|
||||||
@ -1444,7 +1444,7 @@ impl Engine {
|
|||||||
script: &str,
|
script: &str,
|
||||||
) -> Result<T, Box<EvalAltResult>> {
|
) -> Result<T, Box<EvalAltResult>> {
|
||||||
let scripts = [script];
|
let scripts = [script];
|
||||||
let stream = self.lex(&scripts);
|
let stream = self.lex_raw(&scripts, None);
|
||||||
|
|
||||||
// No need to optimize a lone expression
|
// No need to optimize a lone expression
|
||||||
let ast = self.parse_global_expr(&mut stream.peekable(), scope, OptimizationLevel::None)?;
|
let ast = self.parse_global_expr(&mut stream.peekable(), scope, OptimizationLevel::None)?;
|
||||||
@ -1585,7 +1585,7 @@ impl Engine {
|
|||||||
script: &str,
|
script: &str,
|
||||||
) -> Result<(), Box<EvalAltResult>> {
|
) -> Result<(), Box<EvalAltResult>> {
|
||||||
let scripts = [script];
|
let scripts = [script];
|
||||||
let stream = self.lex(&scripts);
|
let stream = self.lex_raw(&scripts, None);
|
||||||
let ast = self.parse(&mut stream.peekable(), scope, self.optimization_level)?;
|
let ast = self.parse(&mut stream.peekable(), scope, self.optimization_level)?;
|
||||||
self.consume_ast_with_scope(scope, &ast)
|
self.consume_ast_with_scope(scope, &ast)
|
||||||
}
|
}
|
||||||
|
@ -203,7 +203,7 @@ impl Engine {
|
|||||||
/// # Examples
|
/// # Examples
|
||||||
///
|
///
|
||||||
/// The following will raise an error during parsing because the `if` keyword is disabled
|
/// The following will raise an error during parsing because the `if` keyword is disabled
|
||||||
/// and is recognized as a variable name!
|
/// and is recognized as a reserved symbol!
|
||||||
///
|
///
|
||||||
/// ```rust,should_panic
|
/// ```rust,should_panic
|
||||||
/// # fn main() -> Result<(), rhai::ParseError> {
|
/// # fn main() -> Result<(), rhai::ParseError> {
|
||||||
@ -214,7 +214,7 @@ impl Engine {
|
|||||||
/// engine.disable_symbol("if"); // disable the 'if' keyword
|
/// engine.disable_symbol("if"); // disable the 'if' keyword
|
||||||
///
|
///
|
||||||
/// engine.compile("let x = if true { 42 } else { 0 };")?;
|
/// engine.compile("let x = if true { 42 } else { 0 };")?;
|
||||||
/// // ^ 'if' is rejected as a reserved keyword
|
/// // ^ 'if' is rejected as a reserved symbol
|
||||||
/// # Ok(())
|
/// # Ok(())
|
||||||
/// # }
|
/// # }
|
||||||
/// ```
|
/// ```
|
||||||
|
@ -1357,7 +1357,9 @@ impl Engine {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
let module = self.search_imports(mods, state, namespace)?;
|
let module = self.search_imports(mods, state, namespace).ok_or_else(|| {
|
||||||
|
EvalAltResult::ErrorModuleNotFound(namespace[0].name.to_string(), namespace[0].pos)
|
||||||
|
})?;
|
||||||
|
|
||||||
// First search in script-defined functions (can override built-in)
|
// First search in script-defined functions (can override built-in)
|
||||||
let func = match module.get_qualified_fn(hash_script) {
|
let func = match module.get_qualified_fn(hash_script) {
|
||||||
|
@ -55,20 +55,19 @@ pub type Locked<T> = crate::stdlib::sync::RwLock<T>;
|
|||||||
|
|
||||||
/// Context of a native Rust function call.
|
/// Context of a native Rust function call.
|
||||||
#[derive(Debug, Copy, Clone)]
|
#[derive(Debug, Copy, Clone)]
|
||||||
pub struct NativeCallContext<'e, 'n, 's, 'a, 'm> {
|
pub struct NativeCallContext<'a> {
|
||||||
engine: &'e Engine,
|
engine: &'a Engine,
|
||||||
fn_name: &'n str,
|
fn_name: &'a str,
|
||||||
source: Option<&'s str>,
|
source: Option<&'a str>,
|
||||||
pub(crate) mods: Option<&'a Imports>,
|
mods: Option<&'a Imports>,
|
||||||
pub(crate) lib: &'m [&'m Module],
|
lib: &'a [&'a Module],
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<'e, 'n, 's, 'a, 'm, M: AsRef<[&'m Module]> + ?Sized>
|
impl<'a, M: AsRef<[&'a Module]> + ?Sized>
|
||||||
From<(&'e Engine, &'n str, Option<&'s str>, &'a Imports, &'m M)>
|
From<(&'a Engine, &'a str, Option<&'a str>, &'a Imports, &'a M)> for NativeCallContext<'a>
|
||||||
for NativeCallContext<'e, 'n, 's, 'a, 'm>
|
|
||||||
{
|
{
|
||||||
#[inline(always)]
|
#[inline(always)]
|
||||||
fn from(value: (&'e Engine, &'n str, Option<&'s str>, &'a Imports, &'m M)) -> Self {
|
fn from(value: (&'a Engine, &'a str, Option<&'a str>, &'a Imports, &'a M)) -> Self {
|
||||||
Self {
|
Self {
|
||||||
engine: value.0,
|
engine: value.0,
|
||||||
fn_name: value.1,
|
fn_name: value.1,
|
||||||
@ -79,11 +78,11 @@ impl<'e, 'n, 's, 'a, 'm, M: AsRef<[&'m Module]> + ?Sized>
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<'e, 'n, 'm, M: AsRef<[&'m Module]> + ?Sized> From<(&'e Engine, &'n str, &'m M)>
|
impl<'a, M: AsRef<[&'a Module]> + ?Sized> From<(&'a Engine, &'a str, &'a M)>
|
||||||
for NativeCallContext<'e, 'n, '_, '_, 'm>
|
for NativeCallContext<'a>
|
||||||
{
|
{
|
||||||
#[inline(always)]
|
#[inline(always)]
|
||||||
fn from(value: (&'e Engine, &'n str, &'m M)) -> Self {
|
fn from(value: (&'a Engine, &'a str, &'a M)) -> Self {
|
||||||
Self {
|
Self {
|
||||||
engine: value.0,
|
engine: value.0,
|
||||||
fn_name: value.1,
|
fn_name: value.1,
|
||||||
@ -94,10 +93,10 @@ impl<'e, 'n, 'm, M: AsRef<[&'m Module]> + ?Sized> From<(&'e Engine, &'n str, &'m
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<'e, 'n, 's, 'a, 'm> NativeCallContext<'e, 'n, 's, 'a, 'm> {
|
impl<'a> NativeCallContext<'a> {
|
||||||
/// Create a new [`NativeCallContext`].
|
/// Create a new [`NativeCallContext`].
|
||||||
#[inline(always)]
|
#[inline(always)]
|
||||||
pub fn new(engine: &'e Engine, fn_name: &'n str, lib: &'m [&'m Module]) -> Self {
|
pub fn new(engine: &'a Engine, fn_name: &'a str, lib: &'a [&Module]) -> Self {
|
||||||
Self {
|
Self {
|
||||||
engine,
|
engine,
|
||||||
fn_name,
|
fn_name,
|
||||||
@ -112,11 +111,11 @@ impl<'e, 'n, 's, 'a, 'm> NativeCallContext<'e, 'n, 's, 'a, 'm> {
|
|||||||
#[cfg(not(feature = "no_module"))]
|
#[cfg(not(feature = "no_module"))]
|
||||||
#[inline(always)]
|
#[inline(always)]
|
||||||
pub fn new_with_all_fields(
|
pub fn new_with_all_fields(
|
||||||
engine: &'e Engine,
|
engine: &'a Engine,
|
||||||
fn_name: &'n str,
|
fn_name: &'a str,
|
||||||
source: &'s Option<&str>,
|
source: &'a Option<&str>,
|
||||||
imports: &'a mut Imports,
|
imports: &'a Imports,
|
||||||
lib: &'m [&'m Module],
|
lib: &'a [&Module],
|
||||||
) -> Self {
|
) -> Self {
|
||||||
Self {
|
Self {
|
||||||
engine,
|
engine,
|
||||||
@ -147,6 +146,14 @@ impl<'e, 'n, 's, 'a, 'm> NativeCallContext<'e, 'n, 's, 'a, 'm> {
|
|||||||
pub fn iter_imports(&self) -> impl Iterator<Item = (&str, &Module)> {
|
pub fn iter_imports(&self) -> impl Iterator<Item = (&str, &Module)> {
|
||||||
self.mods.iter().flat_map(|&m| m.iter())
|
self.mods.iter().flat_map(|&m| m.iter())
|
||||||
}
|
}
|
||||||
|
/// Get an iterator over the current set of modules imported via `import` statements.
|
||||||
|
#[cfg(not(feature = "no_module"))]
|
||||||
|
#[inline(always)]
|
||||||
|
pub(crate) fn iter_imports_raw(
|
||||||
|
&self,
|
||||||
|
) -> impl Iterator<Item = (&ImmutableString, &Shared<Module>)> {
|
||||||
|
self.mods.iter().flat_map(|&m| m.iter_raw())
|
||||||
|
}
|
||||||
/// _(INTERNALS)_ The current set of modules imported via `import` statements.
|
/// _(INTERNALS)_ The current set of modules imported via `import` statements.
|
||||||
/// Available under the `internals` feature only.
|
/// Available under the `internals` feature only.
|
||||||
#[cfg(feature = "internals")]
|
#[cfg(feature = "internals")]
|
||||||
|
@ -110,15 +110,13 @@ fn collect_fn_metadata(ctx: NativeCallContext) -> Array {
|
|||||||
|
|
||||||
let mut list: Array = Default::default();
|
let mut list: Array = Default::default();
|
||||||
|
|
||||||
ctx.lib
|
ctx.iter_namespaces()
|
||||||
.iter()
|
|
||||||
.flat_map(|m| m.iter_script_fn())
|
.flat_map(|m| m.iter_script_fn())
|
||||||
.for_each(|(_, _, _, _, f)| list.push(make_metadata(&dict, None, f).into()));
|
.for_each(|(_, _, _, _, f)| list.push(make_metadata(&dict, None, f).into()));
|
||||||
|
|
||||||
if let Some(mods) = ctx.mods {
|
#[cfg(not(feature = "no_module"))]
|
||||||
mods.iter_raw()
|
ctx.iter_imports_raw()
|
||||||
.for_each(|(ns, m)| scan_module(&mut list, &dict, ns.clone(), m.as_ref()));
|
.for_each(|(ns, m)| scan_module(&mut list, &dict, ns.clone(), m.as_ref()));
|
||||||
}
|
|
||||||
|
|
||||||
list
|
list
|
||||||
}
|
}
|
||||||
|
@ -58,7 +58,7 @@ impl Expression<'_> {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl EvalContext<'_, '_, '_, '_, '_, '_, '_, '_> {
|
impl EvalContext<'_, '_, '_, '_, '_, '_, '_> {
|
||||||
/// Evaluate an [expression tree][Expression].
|
/// Evaluate an [expression tree][Expression].
|
||||||
///
|
///
|
||||||
/// # WARNING - Low Level API
|
/// # WARNING - Low Level API
|
||||||
|
33
src/token.rs
33
src/token.rs
@ -30,7 +30,7 @@ type LERR = LexError;
|
|||||||
const NUM_SEP: char = '_';
|
const NUM_SEP: char = '_';
|
||||||
|
|
||||||
/// A stream of tokens.
|
/// A stream of tokens.
|
||||||
pub type TokenStream<'a, 't> = Peekable<TokenIterator<'a, 't>>;
|
pub type TokenStream<'a> = Peekable<TokenIterator<'a>>;
|
||||||
|
|
||||||
/// A location (line number + character position) in the input script.
|
/// A location (line number + character position) in the input script.
|
||||||
///
|
///
|
||||||
@ -1741,9 +1741,9 @@ impl InputStream for MultiInputsStream<'_> {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/// An iterator on a [`Token`] stream.
|
/// An iterator on a [`Token`] stream.
|
||||||
pub struct TokenIterator<'a, 'e> {
|
pub struct TokenIterator<'a> {
|
||||||
/// Reference to the scripting `Engine`.
|
/// Reference to the scripting `Engine`.
|
||||||
engine: &'e Engine,
|
engine: &'a Engine,
|
||||||
/// Current state.
|
/// Current state.
|
||||||
state: TokenizeState,
|
state: TokenizeState,
|
||||||
/// Current position.
|
/// Current position.
|
||||||
@ -1754,7 +1754,7 @@ pub struct TokenIterator<'a, 'e> {
|
|||||||
map: Option<fn(Token) -> Token>,
|
map: Option<fn(Token) -> Token>,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<'a> Iterator for TokenIterator<'a, '_> {
|
impl<'a> Iterator for TokenIterator<'a> {
|
||||||
type Item = (Token, Position);
|
type Item = (Token, Position);
|
||||||
|
|
||||||
fn next(&mut self) -> Option<Self::Item> {
|
fn next(&mut self) -> Option<Self::Item> {
|
||||||
@ -1837,30 +1837,31 @@ impl<'a> Iterator for TokenIterator<'a, '_> {
|
|||||||
}
|
}
|
||||||
|
|
||||||
impl Engine {
|
impl Engine {
|
||||||
/// Tokenize an input text stream.
|
/// _(INTERNALS)_ Tokenize an input text stream.
|
||||||
|
/// Exported under the `internals` feature only.
|
||||||
|
#[cfg(feature = "internals")]
|
||||||
#[inline(always)]
|
#[inline(always)]
|
||||||
pub fn lex<'a, 'e>(
|
pub fn lex<'a>(&'a self, input: impl IntoIterator<Item = &'a &'a str>) -> TokenIterator<'a> {
|
||||||
&'e self,
|
|
||||||
input: impl IntoIterator<Item = &'a &'a str>,
|
|
||||||
) -> TokenIterator<'a, 'e> {
|
|
||||||
self.lex_raw(input, None)
|
self.lex_raw(input, None)
|
||||||
}
|
}
|
||||||
/// Tokenize an input text stream with a mapping function.
|
/// _(INTERNALS)_ Tokenize an input text stream with a mapping function.
|
||||||
|
/// Exported under the `internals` feature only.
|
||||||
|
#[cfg(feature = "internals")]
|
||||||
#[inline(always)]
|
#[inline(always)]
|
||||||
pub fn lex_with_map<'a, 'e>(
|
pub fn lex_with_map<'a>(
|
||||||
&'e self,
|
&'a self,
|
||||||
input: impl IntoIterator<Item = &'a &'a str>,
|
input: impl IntoIterator<Item = &'a &'a str>,
|
||||||
map: fn(Token) -> Token,
|
map: fn(Token) -> Token,
|
||||||
) -> TokenIterator<'a, 'e> {
|
) -> TokenIterator<'a> {
|
||||||
self.lex_raw(input, Some(map))
|
self.lex_raw(input, Some(map))
|
||||||
}
|
}
|
||||||
/// Tokenize an input text stream with an optional mapping function.
|
/// Tokenize an input text stream with an optional mapping function.
|
||||||
#[inline]
|
#[inline]
|
||||||
fn lex_raw<'a, 'e>(
|
pub(crate) fn lex_raw<'a>(
|
||||||
&'e self,
|
&'a self,
|
||||||
input: impl IntoIterator<Item = &'a &'a str>,
|
input: impl IntoIterator<Item = &'a &'a str>,
|
||||||
map: Option<fn(Token) -> Token>,
|
map: Option<fn(Token) -> Token>,
|
||||||
) -> TokenIterator<'a, 'e> {
|
) -> TokenIterator<'a> {
|
||||||
TokenIterator {
|
TokenIterator {
|
||||||
engine: self,
|
engine: self,
|
||||||
state: TokenizeState {
|
state: TokenizeState {
|
||||||
|
Loading…
Reference in New Issue
Block a user