From 93a1a55aaaae48c0a1f92f8e6f8c8eb88dc01b28 Mon Sep 17 00:00:00 2001 From: Alex Orlenko Date: Sat, 19 Oct 2024 23:10:30 +0100 Subject: [PATCH] Update docs --- src/chunk.rs | 13 +-- src/error.rs | 6 +- src/function.rs | 8 +- src/hook.rs | 6 +- src/lib.rs | 37 +++---- src/multi.rs | 5 +- src/scope.rs | 7 +- src/serde/de.rs | 4 +- src/serde/mod.rs | 6 -- src/state.rs | 196 ++++++++++++++++++++------------------ src/state/raw.rs | 12 +-- src/string.rs | 10 +- src/table.rs | 50 +++++----- src/thread.rs | 44 +++++---- src/traits.rs | 13 +-- src/types.rs | 2 +- src/types/registry_key.rs | 9 +- src/userdata.rs | 176 ++++++++++++++-------------------- src/userdata/cell.rs | 4 +- src/value.rs | 16 +++- 20 files changed, 298 insertions(+), 326 deletions(-) diff --git a/src/chunk.rs b/src/chunk.rs index 37176ad..0aa3e4d 100644 --- a/src/chunk.rs +++ b/src/chunk.rs @@ -14,7 +14,6 @@ use crate::traits::{FromLuaMulti, IntoLuaMulti}; /// Trait for types [loadable by Lua] and convertible to a [`Chunk`] /// /// [loadable by Lua]: https://www.lua.org/manual/5.4/manual.html#3.3.2 -/// [`Chunk`]: crate::Chunk pub trait AsChunk<'a> { /// Returns optional chunk name fn name(&self) -> Option { @@ -95,8 +94,6 @@ impl AsChunk<'static> for PathBuf { } /// Returned from [`Lua::load`] and is used to finalize loading and executing Lua main chunks. -/// -/// [`Lua::load`]: crate::Lua::load #[must_use = "`Chunk`s do nothing unless one of `exec`, `eval`, `call`, or `into_function` are called on them"] pub struct Chunk<'a> { pub(crate) lua: WeakLua, @@ -241,7 +238,7 @@ impl Compiler { /// Compiles the `source` into bytecode. /// - /// Returns `Error::SyntaxError` if the source code is invalid. + /// Returns [`Error::SyntaxError`] if the source code is invalid. pub fn compile(&self, source: impl AsRef<[u8]>) -> Result> { use std::os::raw::c_int; use std::ptr; @@ -361,7 +358,7 @@ impl<'a> Chunk<'a> { /// /// Requires `feature = "async"` /// - /// [`exec`]: #method.exec + /// [`exec`]: Chunk::exec #[cfg(feature = "async")] #[cfg_attr(docsrs, doc(cfg(feature = "async")))] pub async fn exec_async(self) -> Result<()> { @@ -393,7 +390,7 @@ impl<'a> Chunk<'a> { /// /// Requires `feature = "async"` /// - /// [`eval`]: #method.eval + /// [`eval`]: Chunk::eval #[cfg(feature = "async")] #[cfg_attr(docsrs, doc(cfg(feature = "async")))] pub async fn eval_async(self) -> Result @@ -422,7 +419,7 @@ impl<'a> Chunk<'a> { /// /// Requires `feature = "async"` /// - /// [`call`]: #method.call + /// [`call`]: Chunk::call #[cfg(feature = "async")] #[cfg_attr(docsrs, doc(cfg(feature = "async")))] pub async fn call_async(self, args: impl IntoLuaMulti) -> Result @@ -432,7 +429,7 @@ impl<'a> Chunk<'a> { self.into_function()?.call_async(args).await } - /// Load this chunk into a regular `Function`. + /// Load this chunk into a regular [`Function`]. /// /// This simply compiles the chunk without actually executing it. #[cfg_attr(not(feature = "luau"), allow(unused_mut))] diff --git a/src/error.rs b/src/error.rs index db433e6..db4d479 100644 --- a/src/error.rs +++ b/src/error.rs @@ -61,10 +61,12 @@ pub enum Error { /// /// Due to the way `mlua` works, it should not be directly possible to run out of stack space /// during normal use. The only way that this error can be triggered is if a `Function` is - /// called with a huge number of arguments, or a rust callback returns a huge number of return + /// called with a huge number of arguments, or a Rust callback returns a huge number of return /// values. StackError, - /// Too many arguments to `Function::bind`. + /// Too many arguments to [`Function::bind`]. + /// + /// [`Function::bind`]: crate::Function::bind BindError, /// Bad argument received from Lua (usually when calling a function). /// diff --git a/src/function.rs b/src/function.rs index 19e52c3..57e5951 100644 --- a/src/function.rs +++ b/src/function.rs @@ -389,9 +389,9 @@ impl Function { /// If `strip` is true, the binary representation may not include all debug information /// about the function, to save space. /// - /// For Luau a [Compiler] can be used to compile Lua chunks to bytecode. + /// For Luau a [`Compiler`] can be used to compile Lua chunks to bytecode. /// - /// [Compiler]: crate::chunk::Compiler + /// [`Compiler`]: crate::chunk::Compiler #[cfg(not(feature = "luau"))] #[cfg_attr(docsrs, doc(cfg(not(feature = "luau"))))] pub fn dump(&self, strip: bool) -> Vec { @@ -490,10 +490,10 @@ impl Function { /// /// Copies the function prototype and all its upvalues to the /// newly created function. - /// /// This function returns shallow clone (same handle) for Rust/C functions. + /// /// Requires `feature = "luau"` - #[cfg(feature = "luau")] + #[cfg(any(feature = "luau", doc))] #[cfg_attr(docsrs, doc(cfg(feature = "luau")))] pub fn deep_clone(&self) -> Self { let lua = self.0.lua.lock(); diff --git a/src/hook.rs b/src/hook.rs index 3f38c6d..d650dd8 100644 --- a/src/hook.rs +++ b/src/hook.rs @@ -16,9 +16,9 @@ use crate::util::{linenumber_to_usize, ptr_to_lossy_str, ptr_to_str}; /// The `Debug` structure is provided as a parameter to the hook function set with /// [`Lua::set_hook`]. You may call the methods on this structure to retrieve information about the /// Lua code executing at the time that the hook function was called. Further information can be -/// found in the Lua [documentation][lua_doc]. +/// found in the Lua [documentation]. /// -/// [lua_doc]: https://www.lua.org/manual/5.4/manual.html#lua_Debug +/// [documentation]: https://www.lua.org/manual/5.4/manual.html#lua_Debug /// [`Lua::set_hook`]: crate::Lua::set_hook pub struct Debug<'a> { lua: EitherLua<'a>, @@ -66,7 +66,7 @@ impl<'a> Debug<'a> { /// Returns the specific event that triggered the hook. /// - /// For [Lua 5.1] `DebugEvent::TailCall` is used for return events to indicate a return + /// For [Lua 5.1] [`DebugEvent::TailCall`] is used for return events to indicate a return /// from a function that did a tail call. /// /// [Lua 5.1]: https://www.lua.org/manual/5.1/manual.html#pdf-LUA_HOOKTAILRET diff --git a/src/lib.rs b/src/lib.rs index 3769d18..013e253 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -32,41 +32,32 @@ //! [`serde::Serialize`] or [`serde::Deserialize`] can be converted. //! For convenience, additional functionality to handle `NULL` values and arrays is provided. //! -//! The [`Value`] enum implements [`serde::Serialize`] trait to support serializing Lua values -//! (including [`UserData`]) into Rust values. +//! The [`Value`] enum and other types implement [`serde::Serialize`] trait to support serializing +//! Lua values into Rust values. //! //! Requires `feature = "serialize"`. //! //! # Async/await support //! -//! The [`create_async_function`] allows creating non-blocking functions that returns [`Future`]. -//! Lua code with async capabilities can be executed by [`call_async`] family of functions or -//! polling [`AsyncThread`] using any runtime (eg. Tokio). +//! The [`Lua::create_async_function`] allows creating non-blocking functions that returns +//! [`Future`]. Lua code with async capabilities can be executed by [`Function::call_async`] family +//! of functions or polling [`AsyncThread`] using any runtime (eg. Tokio). //! //! Requires `feature = "async"`. //! -//! # `Send` requirement +//! # `Send` and `Sync` support +//! //! By default `mlua` is `!Send`. This can be changed by enabling `feature = "send"` that adds -//! `Send` requirement to [`Function`]s and [`UserData`]. +//! `Send` requirement to Rust functions and [`UserData`] types. +//! +//! In this case [`Lua`] object and their types can be send or used from other threads. Internally +//! access to Lua VM is synchronized using a reentrant mutex that can be locked many times within +//! the same thread. //! //! [Lua programming language]: https://www.lua.org/ -//! [`Lua`]: crate::Lua //! [executing]: crate::Chunk::exec //! [evaluating]: crate::Chunk::eval //! [globals]: crate::Lua::globals -//! [`IntoLua`]: crate::IntoLua -//! [`FromLua`]: crate::FromLua -//! [`IntoLuaMulti`]: crate::IntoLuaMulti -//! [`FromLuaMulti`]: crate::FromLuaMulti -//! [`Function`]: crate::Function -//! [`UserData`]: crate::UserData -//! [`UserDataFields`]: crate::UserDataFields -//! [`UserDataMethods`]: crate::UserDataMethods -//! [`LuaSerdeExt`]: crate::LuaSerdeExt -//! [`Value`]: crate::Value -//! [`create_async_function`]: crate::Lua::create_async_function -//! [`call_async`]: crate::Function::call_async -//! [`AsyncThread`]: crate::AsyncThread //! [`Future`]: std::future::Future //! [`serde::Serialize`]: https://docs.serde.rs/serde/ser/trait.Serialize.html //! [`serde::Deserialize`]: https://docs.serde.rs/serde/de/trait.Deserialize.html @@ -199,10 +190,6 @@ extern crate mlua_derive; /// - The `//` (floor division) operator is unusable, as its start a comment. /// /// Everything else should work. -/// -/// [`AsChunk`]: crate::AsChunk -/// [`UserData`]: crate::UserData -/// [`IntoLua`]: crate::IntoLua #[cfg(feature = "macros")] #[cfg_attr(docsrs, doc(cfg(feature = "macros")))] pub use mlua_derive::chunk; diff --git a/src/multi.rs b/src/multi.rs index 3619588..aded0b6 100644 --- a/src/multi.rs +++ b/src/multi.rs @@ -11,7 +11,7 @@ use crate::traits::{FromLua, FromLuaMulti, IntoLua, IntoLuaMulti}; use crate::util::check_stack; use crate::value::{Nil, Value}; -/// Result is convertible to `MultiValue` following the common Lua idiom of returning the result +/// Result is convertible to [`MultiValue`] following the common Lua idiom of returning the result /// on success, or in the case of an error, returning `nil` and an error message. impl IntoLuaMulti for StdResult { #[inline] @@ -203,9 +203,6 @@ impl FromLuaMulti for MultiValue { /// # Ok(()) /// # } /// ``` -/// -/// [`FromLua`]: crate::FromLua -/// [`MultiValue`]: crate::MultiValue #[derive(Debug, Clone)] pub struct Variadic(Vec); diff --git a/src/scope.rs b/src/scope.rs index 0a0e5be..0aa3b89 100644 --- a/src/scope.rs +++ b/src/scope.rs @@ -148,14 +148,15 @@ impl<'scope, 'env: 'scope> Scope<'scope, 'env> { /// [`Lua::scope`] for more details. /// /// The main limitation that comes from using non-'static userdata is that the produced userdata - /// will no longer have a `TypeId` associated with it, because `TypeId` can only work for + /// will no longer have a [`TypeId`] associated with it, because [`TypeId`] can only work for /// `'static` types. This means that it is impossible, once the userdata is created, to get a - /// reference to it back *out* of an `AnyUserData` handle. This also implies that the + /// reference to it back *out* of an [`AnyUserData`] handle. This also implies that the /// "function" type methods that can be added via [`UserDataMethods`] (the ones that accept - /// `AnyUserData` as a first parameter) are vastly less useful. Also, there is no way to re-use + /// [`AnyUserData`] as a first parameter) are vastly less useful. Also, there is no way to re-use /// a single metatable for multiple non-'static types, so there is a higher cost associated with /// creating the userdata metatable each time a new userdata is created. /// + /// [`TypeId`]: std::any::TypeId /// [`UserDataMethods`]: crate::UserDataMethods pub fn create_userdata(&'scope self, data: T) -> Result where diff --git a/src/serde/de.rs b/src/serde/de.rs index 6c2b2b2..f2a3783 100644 --- a/src/serde/de.rs +++ b/src/serde/de.rs @@ -94,12 +94,12 @@ impl Options { } impl Deserializer { - /// Creates a new Lua Deserializer for the `Value`. + /// Creates a new Lua Deserializer for the [`Value`]. pub fn new(value: Value) -> Self { Self::new_with_options(value, Options::default()) } - /// Creates a new Lua Deserializer for the `Value` with custom options. + /// Creates a new Lua Deserializer for the [`Value`] with custom options. pub fn new_with_options(value: Value, options: Options) -> Self { Deserializer { value, diff --git a/src/serde/mod.rs b/src/serde/mod.rs index 599960e..2ba30e5 100644 --- a/src/serde/mod.rs +++ b/src/serde/mod.rs @@ -106,8 +106,6 @@ pub trait LuaSerdeExt: Sealed { /// /// Requires `feature = "serialize"` /// - /// [`Value`]: crate::Value - /// /// # Example /// /// ``` @@ -133,8 +131,6 @@ pub trait LuaSerdeExt: Sealed { /// /// Requires `feature = "serialize"` /// - /// [`Value`]: crate::Value - /// /// # Example /// /// ``` @@ -164,8 +160,6 @@ pub trait LuaSerdeExt: Sealed { /// /// Requires `feature = "serialize"` /// - /// [`Value`]: crate::Value - /// /// # Example /// /// ``` diff --git a/src/state.rs b/src/state.rs index ffd2b3a..5188bfd 100644 --- a/src/state.rs +++ b/src/state.rs @@ -171,12 +171,10 @@ impl Lua { /// Creates a new Lua state and loads the **safe** subset of the standard libraries. /// /// # Safety - /// The created Lua state would have _some_ safety guarantees and would not allow to load unsafe + /// The created Lua state will have _some_ safety guarantees and will not allow to load unsafe /// standard libraries or C modules. /// /// See [`StdLib`] documentation for a list of unsafe modules that cannot be loaded. - /// - /// [`StdLib`]: crate::StdLib pub fn new() -> Lua { mlua_expect!( Self::new_with(StdLib::ALL_SAFE, LuaOptions::default()), @@ -187,7 +185,7 @@ impl Lua { /// Creates a new Lua state and loads all the standard libraries. /// /// # Safety - /// The created Lua state would not have safety guarantees and would allow to load C modules. + /// The created Lua state will not have safety guarantees and will allow to load C modules. pub unsafe fn unsafe_new() -> Lua { Self::unsafe_new_with(StdLib::ALL, LuaOptions::default()) } @@ -197,12 +195,10 @@ impl Lua { /// Use the [`StdLib`] flags to specify the libraries you want to load. /// /// # Safety - /// The created Lua state would have _some_ safety guarantees and would not allow to load unsafe + /// The created Lua state will have _some_ safety guarantees and will not allow to load unsafe /// standard libraries or C modules. /// /// See [`StdLib`] documentation for a list of unsafe modules that cannot be loaded. - /// - /// [`StdLib`]: crate::StdLib pub fn new_with(libs: StdLib, options: LuaOptions) -> Result { #[cfg(not(feature = "luau"))] if libs.contains(StdLib::DEBUG) { @@ -222,7 +218,7 @@ impl Lua { if libs.contains(StdLib::PACKAGE) { mlua_expect!(lua.disable_c_modules(), "Error disabling C modules"); } - unsafe { lua.lock().set_safe() }; + lua.lock().mark_safe(); Ok(lua) } @@ -233,8 +229,6 @@ impl Lua { /// /// # Safety /// The created Lua state will not have safety guarantees and allow to load C modules. - /// - /// [`StdLib`]: crate::StdLib pub unsafe fn unsafe_new_with(libs: StdLib, options: LuaOptions) -> Lua { // Workaround to avoid stripping a few unused Lua symbols that could be imported // by C modules in unsafe mode @@ -289,6 +283,28 @@ impl Lua { /// /// This method ensures that the Lua instance is locked while the function is called /// and restores Lua stack after the function returns. + /// + /// # Example + /// ``` + /// # use mlua::{Lua, Result}; + /// # fn main() -> Result<()> { + /// let lua = Lua::new(); + /// let n: i32 = unsafe { + /// let nums = (3, 4, 5); + /// lua.exec_raw(nums, |state| { + /// let n = ffi::lua_gettop(state); + /// let mut sum = 0; + /// for i in 1..=n { + /// sum += ffi::lua_tointeger(state, i); + /// } + /// ffi::lua_pop(state, n); + /// ffi::lua_pushinteger(state, sum); + /// }) + /// }?; + /// assert_eq!(n, 12); + /// # Ok(()) + /// # } + /// ``` #[allow(clippy::missing_safety_doc)] pub unsafe fn exec_raw( &self, @@ -399,7 +415,7 @@ impl Lua { // Make sure that Lua is initialized let mut lua = Self::init_from_ptr(state); lua.collect_garbage = false; - // `Lua` is no longer needed and must be dropped at this point to avoid possible memory leak + // `Lua` is no longer needed and must be dropped at this point to avoid memory leak // in case of possible longjmp (lua_error) below drop(lua); @@ -444,6 +460,7 @@ impl Lua { /// /// ``` /// # use mlua::{Lua, Result}; + /// # #[cfg(feature = "luau")] /// # fn main() -> Result<()> { /// let lua = Lua::new(); /// @@ -456,10 +473,13 @@ impl Lua { /// assert_eq!(lua.globals().get::>("var")?, None); /// # Ok(()) /// # } + /// + /// # #[cfg(not(feature = "luau"))] + /// # fn main() {} /// ``` /// /// Requires `feature = "luau"` - #[cfg(any(feature = "luau", docsrs))] + #[cfg(any(feature = "luau", doc))] #[cfg_attr(docsrs, doc(cfg(feature = "luau")))] pub fn sandbox(&self, enabled: bool) -> Result<()> { let lua = self.lock(); @@ -484,7 +504,7 @@ impl Lua { } } - /// Sets a 'hook' function that will periodically be called as Lua code executes. + /// Sets a hook function that will periodically be called as Lua code executes. /// /// When exactly the hook function is called depends on the contents of the `triggers` /// parameter, see [`HookTriggers`] for more details. @@ -496,7 +516,7 @@ impl Lua { /// /// This method sets a hook function for the current thread of this Lua instance. /// If you want to set a hook function for another thread (coroutine), use - /// [`Thread::set_hook()`] instead. + /// [`Thread::set_hook`] instead. /// /// Please note you cannot have more than one hook function set at a time for this Lua instance. /// @@ -521,7 +541,6 @@ impl Lua { /// # } /// ``` /// - /// [`HookTriggers`]: crate::HookTriggers /// [`HookTriggers.every_nth_instruction`]: crate::HookTriggers::every_nth_instruction #[cfg(not(feature = "luau"))] #[cfg_attr(docsrs, doc(cfg(not(feature = "luau"))))] @@ -533,7 +552,7 @@ impl Lua { unsafe { lua.set_thread_hook(lua.state(), triggers, callback) }; } - /// Removes any hook previously set by [`Lua::set_hook()`] or [`Thread::set_hook()`]. + /// Removes any hook previously set by [`Lua::set_hook`] or [`Thread::set_hook`]. /// /// This function has no effect if a hook was not previously set. #[cfg(not(feature = "luau"))] @@ -555,7 +574,7 @@ impl Lua { } } - /// Sets an 'interrupt' function that will periodically be called by Luau VM. + /// Sets an interrupt function that will periodically be called by Luau VM. /// /// Any Luau code is guaranteed to call this handler "eventually" /// (in practice this can happen at any function call or at any loop iteration). @@ -574,6 +593,7 @@ impl Lua { /// ``` /// # use std::sync::{Arc, atomic::{AtomicU64, Ordering}}; /// # use mlua::{Lua, Result, ThreadStatus, VmState}; + /// # #[cfg(feature = "luau")] /// # fn main() -> Result<()> { /// let lua = Lua::new(); /// let count = Arc::new(AtomicU64::new(0)); @@ -596,8 +616,11 @@ impl Lua { /// } /// # Ok(()) /// # } + /// + /// # #[cfg(not(feature = "luau"))] + /// # fn main() {} /// ``` - #[cfg(any(feature = "luau", docsrs))] + #[cfg(any(feature = "luau", doc))] #[cfg_attr(docsrs, doc(cfg(feature = "luau")))] pub fn set_interrupt(&self, callback: F) where @@ -635,10 +658,10 @@ impl Lua { } } - /// Removes any 'interrupt' previously set by `set_interrupt`. + /// Removes any interrupt function previously set by `set_interrupt`. /// /// This function has no effect if an 'interrupt' was not previously set. - #[cfg(any(feature = "luau", docsrs))] + #[cfg(any(feature = "luau", doc))] #[cfg_attr(docsrs, doc(cfg(feature = "luau")))] pub fn remove_interrupt(&self) { let lua = self.lock(); @@ -759,8 +782,8 @@ impl Lua { /// Sets a memory limit (in bytes) on this Lua state. /// - /// Once an allocation occurs that would pass this memory limit, - /// a `Error::MemoryError` is generated instead. + /// Once an allocation occurs that would pass this memory limit, a `Error::MemoryError` is + /// generated instead. /// Returns previous limit (zero means no limit). /// /// Does not work in module mode where Lua state is managed externally. @@ -774,7 +797,7 @@ impl Lua { } } - /// Returns true if the garbage collector is currently running automatically. + /// Returns `true` if the garbage collector is currently running automatically. /// /// Requires `feature = "lua54/lua53/lua52/luau"` #[cfg(any(feature = "lua54", feature = "lua53", feature = "lua52", feature = "luau"))] @@ -809,7 +832,7 @@ impl Lua { /// Steps the garbage collector one indivisible step. /// - /// Returns true if this has finished a collection cycle. + /// Returns `true` if this has finished a collection cycle. pub fn gc_step(&self) -> Result { self.gc_step_kbytes(0) } @@ -828,9 +851,9 @@ impl Lua { } } - /// Sets the 'pause' value of the collector. + /// Sets the `pause` value of the collector. /// - /// Returns the previous value of 'pause'. More information can be found in the Lua + /// Returns the previous value of `pause`. More information can be found in the Lua /// [documentation]. /// /// For Luau this parameter sets GC goal @@ -846,9 +869,9 @@ impl Lua { } } - /// Sets the 'step multiplier' value of the collector. + /// Sets the `step multiplier` value of the collector. /// - /// Returns the previous value of the 'step multiplier'. More information can be found in the + /// Returns the previous value of the `step multiplier`. More information can be found in the /// Lua [documentation]. /// /// [documentation]: https://www.lua.org/manual/5.4/manual.html#2.5 @@ -989,9 +1012,10 @@ impl Lua { } } - /// Create and return an interned Lua string. Lua strings can be arbitrary `[u8]` data including - /// embedded nulls, so in addition to `&str` and `&String`, you can also pass plain `&[u8]` - /// here. + /// Create and return an interned Lua string. + /// + /// Lua strings can be arbitrary `[u8]` data including embedded nulls, so in addition to `&str` + /// and `&String`, you can also pass plain `&[u8]` here. #[inline] pub fn create_string(&self, s: impl AsRef<[u8]>) -> Result { unsafe { self.lock().create_string(s) } @@ -1002,8 +1026,8 @@ impl Lua { /// Requires `feature = "luau"` /// /// [buffer]: https://luau-lang.org/library#buffer-library - #[cfg_attr(docsrs, doc(cfg(feature = "luau")))] #[cfg(any(feature = "luau", doc))] + #[cfg_attr(docsrs, doc(cfg(feature = "luau")))] pub fn create_buffer(&self, buf: impl AsRef<[u8]>) -> Result { let lua = self.lock(); let state = lua.state(); @@ -1014,20 +1038,23 @@ impl Lua { } let _sg = StackGuard::new(state); - check_stack(state, 4)?; + check_stack(state, 3)?; crate::util::push_buffer(state, buf.as_ref(), true)?; Ok(Buffer(lua.pop_ref())) } } /// Creates and returns a new empty table. + #[inline] pub fn create_table(&self) -> Result { self.create_table_with_capacity(0, 0) } /// Creates and returns a new empty table, with the specified capacity. - /// `narr` is a hint for how many elements the table will have as a sequence; - /// `nrec` is a hint for how many other elements the table will have. + /// + /// - `narr` is a hint for how many elements the table will have as a sequence. + /// - `nrec` is a hint for how many other elements the table will have. + /// /// Lua may use these hints to preallocate memory for the new table. pub fn create_table_with_capacity(&self, narr: usize, nrec: usize) -> Result
{ unsafe { self.lock().create_table_with_capacity(narr, nrec) } @@ -1113,9 +1140,6 @@ impl Lua { /// # Ok(()) /// # } /// ``` - /// - /// [`IntoLua`]: crate::IntoLua - /// [`IntoLuaMulti`]: crate::IntoLuaMulti pub fn create_function(&self, func: F) -> Result where F: Fn(&Lua, A) -> Result + MaybeSend + 'static, @@ -1130,10 +1154,7 @@ impl Lua { /// Wraps a Rust mutable closure, creating a callable Lua function handle to it. /// - /// This is a version of [`create_function`] that accepts a FnMut argument. Refer to - /// [`create_function`] for more information about the implementation. - /// - /// [`create_function`]: #method.create_function + /// This is a version of [`Lua::create_function`] that accepts a `FnMut` argument. pub fn create_function_mut(&self, func: F) -> Result where F: FnMut(&Lua, A) -> Result + MaybeSend + 'static, @@ -1162,9 +1183,9 @@ impl Lua { /// call `yield()` passing internal representation of a `Poll::Pending` value. /// /// The function must be called inside Lua coroutine ([`Thread`]) to be able to suspend its - /// execution. An executor should be used to poll [`AsyncThread`] and mlua will take a - /// provided Waker in that case. Otherwise noop waker will be used if try to call the - /// function outside of Rust executors. + /// execution. An executor should be used to poll [`AsyncThread`] and mlua will take a provided + /// Waker in that case. Otherwise noop waker will be used if try to call the function outside of + /// Rust executors. /// /// The family of `call_async()` functions takes care about creating [`Thread`]. /// @@ -1193,7 +1214,6 @@ impl Lua { /// } /// ``` /// - /// [`Thread`]: crate::Thread /// [`AsyncThread`]: crate::AsyncThread #[cfg(feature = "async")] #[cfg_attr(docsrs, doc(cfg(feature = "async")))] @@ -1250,7 +1270,7 @@ impl Lua { /// Creates a Lua userdata object from a custom Rust type. /// - /// You can register the type using [`Lua::register_userdata_type()`] to add fields or methods + /// You can register the type using [`Lua::register_userdata_type`] to add fields or methods /// _before_ calling this method. /// Otherwise, the userdata object will have an empty metatable. /// @@ -1265,7 +1285,7 @@ impl Lua { /// Creates a Lua userdata object from a custom serializable Rust type. /// - /// See [`Lua::create_any_userdata()`] for more details. + /// See [`Lua::create_any_userdata`] for more details. /// /// Requires `feature = "serialize"` #[cfg(feature = "serialize")] @@ -1423,9 +1443,10 @@ impl Lua { } } - /// Returns a handle to the active `Thread`. For calls to `Lua` this will be the main Lua - /// thread, for parameters given to a callback, this will be whatever Lua thread called the - /// callback. + /// Returns a handle to the active `Thread`. + /// + /// For calls to `Lua` this will be the main Lua thread, for parameters given to a callback, + /// this will be whatever Lua thread called the callback. pub fn current_thread(&self) -> Thread { let lua = self.lock(); let state = lua.state(); @@ -1437,26 +1458,16 @@ impl Lua { } } - /// Calls the given function with a `Scope` parameter, giving the function the ability to create - /// userdata and callbacks from rust types that are !Send or non-'static. + /// Calls the given function with a [`Scope`] parameter, giving the function the ability to + /// create userdata and callbacks from Rust types that are `!Send`` or non-`'static`. /// - /// The lifetime of any function or userdata created through `Scope` lasts only until the + /// The lifetime of any function or userdata created through [`Scope`] lasts only until the /// completion of this method call, on completion all such created values are automatically /// dropped and Lua references to them are invalidated. If a script accesses a value created - /// through `Scope` outside of this method, a Lua error will result. Since we can ensure the - /// lifetime of values created through `Scope`, and we know that `Lua` cannot be sent to another - /// thread while `Scope` is live, it is safe to allow !Send datatypes and whose lifetimes only - /// outlive the scope lifetime. - /// - /// Inside the scope callback, all handles created through Scope will share the same unique 'lua - /// lifetime of the parent `Lua`. This allows scoped and non-scoped values to be mixed in - /// API calls, which is very useful (e.g. passing a scoped userdata to a non-scoped function). - /// However, this also enables handles to scoped values to be trivially leaked from the given - /// callback. This is not dangerous, though! After the callback returns, all scoped values are - /// invalidated, which means that though references may exist, the Rust types backing them have - /// dropped. `Function` types will error when called, and `AnyUserData` will be typeless. It - /// would be impossible to prevent handles to scoped values from escaping anyway, since you - /// would always be able to smuggle them through Lua state. + /// through [`Scope`] outside of this method, a Lua error will result. Since we can ensure the + /// lifetime of values created through [`Scope`], and we know that [`Lua`] cannot be sent to + /// another thread while [`Scope`] is live, it is safe to allow `!Send` data types and whose + /// lifetimes only outlive the scope lifetime. pub fn scope<'env, R>( &self, f: impl for<'scope> FnOnce(&'scope mut Scope<'scope, 'env>) -> Result, @@ -1548,41 +1559,41 @@ impl Lua { }) } - /// Converts a value that implements `IntoLua` into a `Value` instance. + /// Converts a value that implements [`IntoLua`] into a [`Value`] instance. #[inline] pub fn pack(&self, t: impl IntoLua) -> Result { t.into_lua(self) } - /// Converts a `Value` instance into a value that implements `FromLua`. + /// Converts a [`Value`] instance into a value that implements [`FromLua`]. #[inline] pub fn unpack(&self, value: Value) -> Result { T::from_lua(value, self) } - /// Converts a value that implements `IntoLua` into a `FromLua` variant. + /// Converts a value that implements [`IntoLua`] into a [`FromLua`] variant. #[inline] pub fn convert(&self, value: impl IntoLua) -> Result { U::from_lua(value.into_lua(self)?, self) } - /// Converts a value that implements `IntoLuaMulti` into a `MultiValue` instance. + /// Converts a value that implements [`IntoLuaMulti`] into a [`MultiValue`] instance. #[inline] pub fn pack_multi(&self, t: impl IntoLuaMulti) -> Result { t.into_lua_multi(self) } - /// Converts a `MultiValue` instance into a value that implements `FromLuaMulti`. + /// Converts a [`MultiValue`] instance into a value that implements [`FromLuaMulti`]. #[inline] pub fn unpack_multi(&self, value: MultiValue) -> Result { T::from_lua_multi(value, self) } - /// Set a value in the Lua registry based on a string name. + /// Set a value in the Lua registry based on a string key. /// - /// This value will be available to rust from all `Lua` instances which share the same main + /// This value will be available to Rust from all Lua instances which share the same main /// state. - pub fn set_named_registry_value(&self, name: &str, t: impl IntoLua) -> Result<()> { + pub fn set_named_registry_value(&self, key: &str, t: impl IntoLua) -> Result<()> { let lua = self.lock(); let state = lua.state(); unsafe { @@ -1590,15 +1601,15 @@ impl Lua { check_stack(state, 5)?; lua.push(t)?; - rawset_field(state, ffi::LUA_REGISTRYINDEX, name) + rawset_field(state, ffi::LUA_REGISTRYINDEX, key) } } - /// Get a value from the Lua registry based on a string name. + /// Get a value from the Lua registry based on a string key. /// /// Any Lua instance which shares the underlying main state may call this method to /// get a value previously set by [`Lua::set_named_registry_value`]. - pub fn named_registry_value(&self, name: &str) -> Result + pub fn named_registry_value(&self, key: &str) -> Result where T: FromLua, { @@ -1609,7 +1620,7 @@ impl Lua { check_stack(state, 3)?; let protect = !lua.unlikely_memory_error(); - push_string(state, name.as_bytes(), protect)?; + push_string(state, key.as_bytes(), protect)?; ffi::lua_rawget(state, ffi::LUA_REGISTRYINDEX); T::from_stack(-1, &lua) @@ -1618,14 +1629,15 @@ impl Lua { /// Removes a named value in the Lua registry. /// - /// Equivalent to calling [`Lua::set_named_registry_value`] with a value of Nil. - pub fn unset_named_registry_value(&self, name: &str) -> Result<()> { - self.set_named_registry_value(name, Nil) + /// Equivalent to calling [`Lua::set_named_registry_value`] with a value of [`Nil`]. + #[inline] + pub fn unset_named_registry_value(&self, key: &str) -> Result<()> { + self.set_named_registry_value(key, Nil) } /// Place a value in the Lua registry with an auto-generated key. /// - /// This value will be available to Rust from all `Lua` instances which share the same main + /// This value will be available to Rust from all Lua instances which share the same main /// state. /// /// Be warned, garbage collection of values held inside the registry is not automatic, see @@ -1667,7 +1679,7 @@ impl Lua { } } - /// Get a value from the Lua registry by its `RegistryKey` + /// Get a value from the Lua registry by its [`RegistryKey`] /// /// Any Lua instance which shares the underlying main state may call this method to get a value /// previously placed by [`Lua::create_registry_value`]. @@ -1702,9 +1714,7 @@ impl Lua { return Err(Error::MismatchedRegistryKey); } - unsafe { - ffi::luaL_unref(lua.state(), ffi::LUA_REGISTRYINDEX, key.take()); - } + unsafe { ffi::luaL_unref(lua.state(), ffi::LUA_REGISTRYINDEX, key.take()) }; Ok(()) } @@ -1750,8 +1760,8 @@ impl Lua { Ok(()) } - /// Returns true if the given [`RegistryKey`] was created by a [`Lua`] which shares the - /// underlying main state with this [`Lua`] instance. + /// Returns true if the given [`RegistryKey`] was created by a Lua which shares the + /// underlying main state with this Lua instance. /// /// Other than this, methods that accept a [`RegistryKey`] will return /// [`Error::MismatchedRegistryKey`] if passed a [`RegistryKey`] that was not created with a @@ -1823,14 +1833,14 @@ impl Lua { /// - `Err(data)` if the data object of type `T` was not inserted because the container is /// currently borrowed. /// - /// See [`Lua::set_app_data()`] for examples. + /// See [`Lua::set_app_data`] for examples. pub fn try_set_app_data(&self, data: T) -> StdResult, T> { let lua = self.lock(); let extra = unsafe { &*lua.extra.get() }; extra.app_data.try_insert(data) } - /// Gets a reference to an application data object stored by [`Lua::set_app_data()`] of type + /// Gets a reference to an application data object stored by [`Lua::set_app_data`] of type /// `T`. /// /// # Panics @@ -1844,7 +1854,7 @@ impl Lua { extra.app_data.borrow(Some(guard)) } - /// Gets a mutable reference to an application data object stored by [`Lua::set_app_data()`] of + /// Gets a mutable reference to an application data object stored by [`Lua::set_app_data`] of /// type `T`. /// /// # Panics diff --git a/src/state/raw.rs b/src/state/raw.rs index c756356..3a47764 100644 --- a/src/state/raw.rs +++ b/src/state/raw.rs @@ -129,7 +129,7 @@ impl RawLua { let extra = rawlua.lock().extra.get(); mlua_expect!( - load_from_std_lib(state, libs), + load_std_libs(state, libs), "Error during loading standard libraries" ); (*extra).libs |= libs; @@ -238,8 +238,8 @@ impl RawLua { /// Marks the Lua state as safe. #[inline(always)] - pub(super) unsafe fn set_safe(&self) { - (*self.extra.get()).safe = true; + pub(super) fn mark_safe(&self) { + unsafe { (*self.extra.get()).safe = true }; } /// Loads the specified subset of the standard libraries into an existing Lua state. @@ -263,7 +263,7 @@ impl RawLua { )); } - let res = load_from_std_lib(self.main_state, libs); + let res = load_std_libs(self.main_state, libs); // If `package` library loaded into a safe lua state then disable C modules let curr_libs = (*self.extra.get()).libs; @@ -1100,7 +1100,7 @@ impl RawLua { #[cfg(any(feature = "lua54", feature = "lua53", feature = "lua52", feature = "luau"))] unsafe { if !(*self.extra.get()).libs.contains(StdLib::COROUTINE) { - load_from_std_lib(self.main_state, StdLib::COROUTINE)?; + load_std_libs(self.main_state, StdLib::COROUTINE)?; (*self.extra.get()).libs |= StdLib::COROUTINE; } } @@ -1249,7 +1249,7 @@ impl RawLua { } // Uses 3 stack spaces -unsafe fn load_from_std_lib(state: *mut ffi::lua_State, libs: StdLib) -> Result<()> { +unsafe fn load_std_libs(state: *mut ffi::lua_State, libs: StdLib) -> Result<()> { #[inline(always)] pub unsafe fn requiref( state: *mut ffi::lua_State, diff --git a/src/string.rs b/src/string.rs index 364010f..b8fd7c0 100644 --- a/src/string.rs +++ b/src/string.rs @@ -5,16 +5,16 @@ use std::os::raw::{c_int, c_void}; use std::string::String as StdString; use std::{cmp, fmt, slice, str}; +use crate::error::{Error, Result}; +use crate::state::Lua; +use crate::types::{LuaType, ValueRef}; + #[cfg(feature = "serialize")] use { serde::ser::{Serialize, Serializer}, std::result::Result as StdResult, }; -use crate::error::{Error, Result}; -use crate::state::Lua; -use crate::types::{LuaType, ValueRef}; - /// Handle to an internal Lua string. /// /// Unlike Rust strings, Lua strings may not be valid UTF-8. @@ -148,7 +148,7 @@ impl fmt::Debug for String { } } -// Lua strings are basically &[u8] slices, so implement PartialEq for anything resembling that. +// Lua strings are basically `&[u8]` slices, so implement `PartialEq` for anything resembling that. // // This makes our `String` comparable with `Vec`, `[u8]`, `&str` and `String`. // diff --git a/src/table.rs b/src/table.rs index 2ad512f..b632500 100644 --- a/src/table.rs +++ b/src/table.rs @@ -4,13 +4,6 @@ use std::marker::PhantomData; use std::os::raw::{c_int, c_void}; use std::string::String as StdString; -#[cfg(feature = "serialize")] -use { - rustc_hash::FxHashSet, - serde::ser::{Serialize, SerializeMap, SerializeSeq, Serializer}, - std::{cell::RefCell, rc::Rc, result::Result as StdResult}, -}; - use crate::error::{Error, Result}; use crate::function::Function; use crate::state::{LuaGuard, RawLua}; @@ -22,6 +15,13 @@ use crate::value::{Nil, Value}; #[cfg(feature = "async")] use futures_util::future::{self, Either, Future}; +#[cfg(feature = "serialize")] +use { + rustc_hash::FxHashSet, + serde::ser::{Serialize, SerializeMap, SerializeSeq, Serializer}, + std::{cell::RefCell, rc::Rc, result::Result as StdResult}, +}; + /// Handle to an internal Lua table. #[derive(Clone, PartialEq)] pub struct Table(pub(crate) ValueRef); @@ -59,7 +59,7 @@ impl Table { /// # } /// ``` /// - /// [`raw_set`]: #method.raw_set + /// [`raw_set`]: Table::raw_set pub fn set(&self, key: impl IntoLua, value: impl IntoLua) -> Result<()> { // Fast track (skip protected call) if !self.has_metatable() { @@ -106,7 +106,7 @@ impl Table { /// # } /// ``` /// - /// [`raw_get`]: #method.raw_get + /// [`raw_get`]: Table::raw_get pub fn get(&self, key: impl IntoLua) -> Result { // Fast track (skip protected call) if !self.has_metatable() { @@ -282,7 +282,9 @@ impl Table { } /// Inserts element value at position `idx` to the table, shifting up the elements from - /// `table[idx]`. The worst case complexity is O(n), where n is the table length. + /// `table[idx]`. + /// + /// The worst case complexity is O(n), where n is the table length. pub fn raw_insert(&self, idx: Integer, value: impl IntoLua) -> Result<()> { let size = self.raw_len() as Integer; if idx < 1 || idx > size + 1 { @@ -361,8 +363,8 @@ impl Table { /// Removes a key from the table. /// /// If `key` is an integer, mlua shifts down the elements from `table[key+1]`, - /// and erases element `table[key]`. The complexity is O(n) in the worst case, - /// where n is the table length. + /// and erases element `table[key]`. The complexity is `O(n)` in the worst case, + /// where `n` is the table length. /// /// For other key types this is equivalent to setting `table[key] = nil`. pub fn raw_remove(&self, key: impl IntoLua) -> Result<()> { @@ -437,9 +439,8 @@ impl Table { /// Returns the result of the Lua `#` operator. /// - /// This might invoke the `__len` metamethod. Use the [`raw_len`] method if that is not desired. - /// - /// [`raw_len`]: #method.raw_len + /// This might invoke the `__len` metamethod. Use the [`Table::raw_len`] method if that is not + /// desired. pub fn len(&self) -> Result { // Fast track (skip protected call) if !self.has_metatable() { @@ -491,7 +492,9 @@ impl Table { /// Returns a reference to the metatable of this table, or `None` if no metatable is set. /// - /// Unlike the `getmetatable` Lua function, this method ignores the `__metatable` field. + /// Unlike the [`getmetatable`] Lua function, this method ignores the `__metatable` field. + /// + /// [`getmetatable`]: https://www.lua.org/manual/5.4/manual.html#pdf-getmetatable pub fn metatable(&self) -> Option
{ let lua = self.0.lua.lock(); let state = lua.state(); @@ -621,7 +624,6 @@ impl Table { /// # } /// ``` /// - /// [`Result`]: crate::Result /// [Lua manual]: http://www.lua.org/manual/5.4/manual.html#pdf-next pub fn pairs(&self) -> TablePairs { TablePairs { @@ -688,10 +690,6 @@ impl Table { /// # Ok(()) /// # } /// ``` - /// - /// [`pairs`]: #method.pairs - /// [`Result`]: crate::Result - /// [Lua manual]: http://www.lua.org/manual/5.4/manual.html#pdf-next pub fn sequence_values(&self) -> TableSequence { TableSequence { guard: self.0.lua.lock(), @@ -701,7 +699,7 @@ impl Table { } } - #[cfg(feature = "serialize")] + /// Iterates over the sequence part of the table, invoking the given closure on each value. pub(crate) fn for_each_value(&self, mut f: impl FnMut(V) -> Result<()>) -> Result<()> where V: FromLua, @@ -860,6 +858,10 @@ where } } +impl LuaType for Table { + const TYPE_ID: c_int = ffi::LUA_TTABLE; +} + impl ObjectLike for Table { #[inline] fn get(&self, key: impl IntoLua) -> Result { @@ -954,10 +956,6 @@ impl Serialize for Table { } } -impl LuaType for Table { - const TYPE_ID: c_int = ffi::LUA_TTABLE; -} - #[cfg(feature = "serialize")] impl<'a> SerializableTable<'a> { #[inline] diff --git a/src/thread.rs b/src/thread.rs index 1669a0b..aaec30a 100644 --- a/src/thread.rs +++ b/src/thread.rs @@ -75,17 +75,17 @@ impl Thread { /// Resumes execution of this thread. /// - /// Equivalent to `coroutine.resume`. + /// Equivalent to [`coroutine.resume`]. /// - /// Passes `args` as arguments to the thread. If the coroutine has called `coroutine.yield`, it - /// will return these arguments. Otherwise, the coroutine wasn't yet started, so the arguments - /// are passed to its main function. + /// Passes `args` as arguments to the thread. If the coroutine has called [`coroutine.yield`], + /// it will return these arguments. Otherwise, the coroutine wasn't yet started, so the + /// arguments are passed to its main function. /// - /// If the thread is no longer in `Active` state (meaning it has finished execution or - /// encountered an error), this will return `Err(CoroutineInactive)`, otherwise will return `Ok` - /// as follows: + /// If the thread is no longer resumable (meaning it has finished execution or encountered an + /// error), this will return [`Error::CoroutineUnresumable`], otherwise will return `Ok` as + /// follows: /// - /// If the thread calls `coroutine.yield`, returns the values passed to `yield`. If the thread + /// If the thread calls [`coroutine.yield`], returns the values passed to `yield`. If the thread /// `return`s values from its main function, returns those. /// /// # Examples @@ -114,6 +114,9 @@ impl Thread { /// # Ok(()) /// # } /// ``` + /// + /// [`coroutine.resume`]: https://www.lua.org/manual/5.4/manual.html#pdf-coroutine.resume + /// [`coroutine.yield`]: https://www.lua.org/manual/5.4/manual.html#pdf-coroutine.yield pub fn resume(&self, args: impl IntoLuaMulti) -> Result where R: FromLuaMulti, @@ -187,10 +190,10 @@ impl Thread { } } - /// Sets a 'hook' function that will periodically be called as Lua code executes. + /// Sets a hook function that will periodically be called as Lua code executes. /// - /// This function is similar or [`Lua::set_hook()`] except that it sets for the thread. - /// To remove a hook call [`Lua::remove_hook()`]. + /// This function is similar or [`Lua::set_hook`] except that it sets for the thread. + /// To remove a hook call [`Lua::remove_hook`]. #[cfg(not(feature = "luau"))] #[cfg_attr(docsrs, doc(cfg(not(feature = "luau"))))] pub fn set_hook(&self, triggers: HookTriggers, callback: F) @@ -252,21 +255,22 @@ impl Thread { } } - /// Converts Thread to an AsyncThread which implements [`Future`] and [`Stream`] traits. + /// Converts [`Thread`] to an [`AsyncThread`] which implements [`Future`] and [`Stream`] traits. /// /// `args` are passed as arguments to the thread function for first call. - /// The object calls [`resume()`] while polling and also allows to run rust futures + /// The object calls [`resume`] while polling and also allow to run Rust futures /// to completion using an executor. /// - /// Using AsyncThread as a Stream allows to iterate through `coroutine.yield()` - /// values whereas Future version discards that values and poll until the final + /// Using [`AsyncThread`] as a [`Stream`] allow to iterate through [`coroutine.yield`] + /// values whereas [`Future`] version discards that values and poll until the final /// one (returned from the thread function). /// /// Requires `feature = "async"` /// /// [`Future`]: std::future::Future /// [`Stream`]: futures_util::stream::Stream - /// [`resume()`]: https://www.lua.org/manual/5.4/manual.html#lua_resume + /// [`resume`]: https://www.lua.org/manual/5.4/manual.html#lua_resume + /// [`coroutine.yield`]: https://www.lua.org/manual/5.4/manual.html#pdf-coroutine.yield /// /// # Examples /// @@ -316,7 +320,7 @@ impl Thread { /// Under the hood replaces the global environment table with a new table, /// that performs writes locally and proxies reads to caller's global environment. /// - /// This mode ideally should be used together with the global sandbox mode [`Lua::sandbox()`]. + /// This mode ideally should be used together with the global sandbox mode [`Lua::sandbox`]. /// /// Please note that Luau links environment table with chunk when loading it into Lua state. /// Therefore you need to load chunks into a thread to link with the thread environment. @@ -325,6 +329,7 @@ impl Thread { /// /// ``` /// # use mlua::{Lua, Result}; + /// # #[cfg(feature = "luau")] /// # fn main() -> Result<()> { /// let lua = Lua::new(); /// let thread = lua.create_thread(lua.create_function(|lua2, ()| { @@ -339,10 +344,13 @@ impl Thread { /// assert_eq!(lua.globals().get::>("var")?, None); /// # Ok(()) /// # } + /// + /// # #[cfg(not(feature = "luau"))] + /// # fn main() { } /// ``` /// /// Requires `feature = "luau"` - #[cfg(any(feature = "luau", docsrs))] + #[cfg(any(feature = "luau", doc))] #[cfg_attr(docsrs, doc(cfg(feature = "luau")))] #[doc(hidden)] pub fn sandbox(&self) -> Result<()> { diff --git a/src/traits.rs b/src/traits.rs index 46adfbf..0156c01 100644 --- a/src/traits.rs +++ b/src/traits.rs @@ -13,7 +13,7 @@ use crate::value::Value; #[cfg(feature = "async")] use std::future::Future; -/// Trait for types convertible to `Value`. +/// Trait for types convertible to [`Value`]. pub trait IntoLua: Sized { /// Performs the conversion. fn into_lua(self, lua: &Lua) -> Result; @@ -29,7 +29,7 @@ pub trait IntoLua: Sized { } } -/// Trait for types convertible from `Value`. +/// Trait for types convertible from [`Value`]. pub trait FromLua: Sized { /// Performs the conversion. fn from_lua(value: Value, lua: &Lua) -> Result; @@ -71,8 +71,8 @@ pub trait FromLua: Sized { /// Trait for types convertible to any number of Lua values. /// -/// This is a generalization of `IntoLua`, allowing any number of resulting Lua values instead of -/// just one. Any type that implements `IntoLua` will automatically implement this trait. +/// This is a generalization of [`IntoLua`], allowing any number of resulting Lua values instead of +/// just one. Any type that implements [`IntoLua`] will automatically implement this trait. pub trait IntoLuaMulti: Sized { /// Performs the conversion. fn into_lua_multi(self, lua: &Lua) -> Result; @@ -97,8 +97,9 @@ pub trait IntoLuaMulti: Sized { /// Trait for types that can be created from an arbitrary number of Lua values. /// -/// This is a generalization of `FromLua`, allowing an arbitrary number of Lua values to participate -/// in the conversion. Any type that implements `FromLua` will automatically implement this trait. +/// This is a generalization of [`FromLua`], allowing an arbitrary number of Lua values to +/// participate in the conversion. Any type that implements [`FromLua`] will automatically +/// implement this trait. pub trait FromLuaMulti: Sized { /// Performs the conversion. /// diff --git a/src/types.rs b/src/types.rs index 12f4083..a5a7405 100644 --- a/src/types.rs +++ b/src/types.rs @@ -66,7 +66,7 @@ pub(crate) type AsyncCallbackUpvalue = Upvalue; #[cfg(feature = "async")] pub(crate) type AsyncPollUpvalue = Upvalue>>; -/// Type to set next Luau VM action after executing interrupt function. +/// Type to set next Lua VM action after executing interrupt or hook function. pub enum VmState { Continue, /// Yield the current thread. diff --git a/src/types/registry_key.rs b/src/types/registry_key.rs index b92b103..6df0002 100644 --- a/src/types/registry_key.rs +++ b/src/types/registry_key.rs @@ -12,17 +12,16 @@ use parking_lot::Mutex; /// and instances not manually removed can be garbage collected with /// [`Lua::expire_registry_values`]. /// -/// Be warned, If you place this into Lua via a [`UserData`] type or a rust callback, it is *very -/// easy* to accidentally cause reference cycles that the Lua garbage collector cannot resolve. -/// Instead of placing a [`RegistryKey`] into a [`UserData`] type, prefer instead to use -/// [`AnyUserData::set_user_value`] / [`AnyUserData::user_value`]. +/// Be warned, If you place this into Lua via a [`UserData`] type or a Rust callback, it is *easy* +/// to accidentally cause reference cycles that the Lua garbage collector cannot resolve. Instead of +/// placing a [`RegistryKey`] into a [`UserData`] type, consider to use +/// [`AnyUserData::set_user_value`]. /// /// [`UserData`]: crate::UserData /// [`RegistryKey`]: crate::RegistryKey /// [`Lua::remove_registry_value`]: crate::Lua::remove_registry_value /// [`Lua::expire_registry_values`]: crate::Lua::expire_registry_values /// [`AnyUserData::set_user_value`]: crate::AnyUserData::set_user_value -/// [`AnyUserData::user_value`]: crate::AnyUserData::user_value pub struct RegistryKey { pub(crate) registry_id: i32, pub(crate) unref_list: Arc>>>, diff --git a/src/userdata.rs b/src/userdata.rs index 4a668f6..db1f37a 100644 --- a/src/userdata.rs +++ b/src/userdata.rs @@ -5,15 +5,6 @@ use std::hash::Hash; use std::os::raw::{c_char, c_void}; use std::string::String as StdString; -#[cfg(feature = "async")] -use std::future::Future; - -#[cfg(feature = "serialize")] -use { - serde::ser::{self, Serialize, Serializer}, - std::result::Result as StdResult, -}; - use crate::error::{Error, Result}; use crate::function::Function; use crate::state::Lua; @@ -24,6 +15,15 @@ use crate::types::{MaybeSend, ValueRef}; use crate::util::{check_stack, get_userdata, push_string, take_userdata, StackGuard}; use crate::value::Value; +#[cfg(feature = "async")] +use std::future::Future; + +#[cfg(feature = "serialize")] +use { + serde::ser::{self, Serialize, Serializer}, + std::result::Result as StdResult, +}; + // Re-export for convenience pub(crate) use cell::UserDataStorage; pub use cell::{UserDataRef, UserDataRefMut}; @@ -34,8 +34,6 @@ pub use registry::UserDataRegistry; /// /// Currently, this mechanism does not allow overriding the `__gc` metamethod, since there is /// generally no need to do so: [`UserData`] implementors can instead just implement `Drop`. -/// -/// [`UserData`]: crate::UserData #[derive(Debug, Clone, Copy, PartialEq, Eq, Hash)] #[non_exhaustive] pub enum MetaMethod { @@ -243,8 +241,6 @@ impl AsRef for MetaMethod { } /// Method registry for [`UserData`] implementors. -/// -/// [`UserData`]: crate::UserData pub trait UserDataMethods { /// Add a regular method which accepts a `&T` as the first parameter. /// @@ -263,20 +259,20 @@ pub trait UserDataMethods { /// /// Refer to [`add_method`] for more information about the implementation. /// - /// [`add_method`]: #method.add_method + /// [`add_method`]: UserDataMethods::add_method fn add_method_mut(&mut self, name: impl ToString, method: M) where M: FnMut(&Lua, &mut T, A) -> Result + MaybeSend + 'static, A: FromLuaMulti, R: IntoLuaMulti; - /// Add an async method which accepts a `&T` as the first parameter and returns Future. + /// Add an async method which accepts a `&T` as the first parameter and returns [`Future`]. /// /// Refer to [`add_method`] for more information about the implementation. /// /// Requires `feature = "async"` /// - /// [`add_method`]: #method.add_method + /// [`add_method`]: UserDataMethods::add_method #[cfg(feature = "async")] #[cfg_attr(docsrs, doc(cfg(feature = "async")))] fn add_async_method(&mut self, name: impl ToString, method: M) @@ -287,13 +283,13 @@ pub trait UserDataMethods { MR: Future> + MaybeSend + 'static, R: IntoLuaMulti; - /// Add an async method which accepts a `&mut T` as the first parameter and returns Future. + /// Add an async method which accepts a `&mut T` as the first parameter and returns [`Future`]. /// /// Refer to [`add_method`] for more information about the implementation. /// /// Requires `feature = "async"` /// - /// [`add_method`]: #method.add_method + /// [`add_method`]: UserDataMethods::add_method #[cfg(feature = "async")] #[cfg_attr(docsrs, doc(cfg(feature = "async")))] fn add_async_method_mut(&mut self, name: impl ToString, method: M) @@ -304,16 +300,11 @@ pub trait UserDataMethods { MR: Future> + MaybeSend + 'static, R: IntoLuaMulti; - /// Add a regular method as a function which accepts generic arguments, the first argument will - /// be a [`AnyUserData`] of type `T` if the method is called with Lua method syntax: - /// `my_userdata:my_method(arg1, arg2)`, or it is passed in as the first argument: - /// `my_userdata.my_method(my_userdata, arg1, arg2)`. + /// Add a regular method as a function which accepts generic arguments. /// - /// Prefer to use [`add_method`] or [`add_method_mut`] as they are easier to use. - /// - /// [`AnyUserData`]: crate::AnyUserData - /// [`add_method`]: #method.add_method - /// [`add_method_mut`]: #method.add_method_mut + /// The first argument will be a [`AnyUserData`] of type `T` if the method is called with Lua + /// method syntax: `my_userdata:my_method(arg1, arg2)`, or it is passed in as the first + /// argument: `my_userdata.my_method(my_userdata, arg1, arg2)`. fn add_function(&mut self, name: impl ToString, function: F) where F: Fn(&Lua, A) -> Result + MaybeSend + 'static, @@ -322,23 +313,23 @@ pub trait UserDataMethods { /// Add a regular method as a mutable function which accepts generic arguments. /// - /// This is a version of [`add_function`] that accepts a FnMut argument. + /// This is a version of [`add_function`] that accepts a `FnMut` argument. /// - /// [`add_function`]: #method.add_function + /// [`add_function`]: UserDataMethods::add_function fn add_function_mut(&mut self, name: impl ToString, function: F) where F: FnMut(&Lua, A) -> Result + MaybeSend + 'static, A: FromLuaMulti, R: IntoLuaMulti; - /// Add a regular method as an async function which accepts generic arguments - /// and returns Future. + /// Add a regular method as an async function which accepts generic arguments and returns + /// [`Future`]. /// /// This is an async version of [`add_function`]. /// /// Requires `feature = "async"` /// - /// [`add_function`]: #method.add_function + /// [`add_function`]: UserDataMethods::add_function #[cfg(feature = "async")] #[cfg_attr(docsrs, doc(cfg(feature = "async")))] fn add_async_function(&mut self, name: impl ToString, function: F) @@ -355,7 +346,7 @@ pub trait UserDataMethods { /// This can cause an error with certain binary metamethods that can trigger if only the right /// side has a metatable. To prevent this, use [`add_meta_function`]. /// - /// [`add_meta_function`]: #method.add_meta_function + /// [`add_meta_function`]: UserDataMethods::add_meta_function fn add_meta_method(&mut self, name: impl ToString, method: M) where M: Fn(&Lua, &T, A) -> Result + MaybeSend + 'static, @@ -369,20 +360,20 @@ pub trait UserDataMethods { /// This can cause an error with certain binary metamethods that can trigger if only the right /// side has a metatable. To prevent this, use [`add_meta_function`]. /// - /// [`add_meta_function`]: #method.add_meta_function + /// [`add_meta_function`]: UserDataMethods::add_meta_function fn add_meta_method_mut(&mut self, name: impl ToString, method: M) where M: FnMut(&Lua, &mut T, A) -> Result + MaybeSend + 'static, A: FromLuaMulti, R: IntoLuaMulti; - /// Add an async metamethod which accepts a `&T` as the first parameter and returns Future. + /// Add an async metamethod which accepts a `&T` as the first parameter and returns [`Future`]. /// /// This is an async version of [`add_meta_method`]. /// /// Requires `feature = "async"` /// - /// [`add_meta_method`]: #method.add_meta_method + /// [`add_meta_method`]: UserDataMethods::add_meta_method #[cfg(all(feature = "async", not(any(feature = "lua51", feature = "luau"))))] #[cfg_attr(docsrs, doc(cfg(feature = "async")))] fn add_async_meta_method(&mut self, name: impl ToString, method: M) @@ -393,13 +384,14 @@ pub trait UserDataMethods { MR: Future> + MaybeSend + 'static, R: IntoLuaMulti; - /// Add an async metamethod which accepts a `&mut T` as the first parameter and returns Future. + /// Add an async metamethod which accepts a `&mut T` as the first parameter and returns + /// [`Future`]. /// /// This is an async version of [`add_meta_method_mut`]. /// /// Requires `feature = "async"` /// - /// [`add_meta_method_mut`]: #method.add_meta_method_mut + /// [`add_meta_method_mut`]: UserDataMethods::add_meta_method_mut #[cfg(all(feature = "async", not(any(feature = "lua51", feature = "luau"))))] #[cfg_attr(docsrs, doc(cfg(feature = "async")))] fn add_async_meta_method_mut(&mut self, name: impl ToString, method: M) @@ -423,22 +415,22 @@ pub trait UserDataMethods { /// Add a metamethod as a mutable function which accepts generic arguments. /// - /// This is a version of [`add_meta_function`] that accepts a FnMut argument. + /// This is a version of [`add_meta_function`] that accepts a `FnMut` argument. /// - /// [`add_meta_function`]: #method.add_meta_function + /// [`add_meta_function`]: UserDataMethods::add_meta_function fn add_meta_function_mut(&mut self, name: impl ToString, function: F) where F: FnMut(&Lua, A) -> Result + MaybeSend + 'static, A: FromLuaMulti, R: IntoLuaMulti; - /// Add a metamethod which accepts generic arguments and returns Future. + /// Add a metamethod which accepts generic arguments and returns [`Future`]. /// /// This is an async version of [`add_meta_function`]. /// /// Requires `feature = "async"` /// - /// [`add_meta_function`]: #method.add_meta_function + /// [`add_meta_function`]: UserDataMethods::add_meta_function #[cfg(all(feature = "async", not(any(feature = "lua51", feature = "luau"))))] #[cfg_attr(docsrs, doc(cfg(feature = "async")))] fn add_async_meta_function(&mut self, name: impl ToString, function: F) @@ -450,15 +442,13 @@ pub trait UserDataMethods { } /// Field registry for [`UserData`] implementors. -/// -/// [`UserData`]: crate::UserData pub trait UserDataFields { - /// Add a static field to the `UserData`. + /// Add a static field to the [`UserData`]. /// /// Static fields are implemented by updating the `__index` metamethod and returning the /// accessed field. This allows them to be used with the expected `userdata.field` syntax. /// - /// Static fields are usually shared between all instances of the `UserData` of the same type. + /// Static fields are usually shared between all instances of the [`UserData`] of the same type. /// /// If `add_meta_method` is used to set the `__index` metamethod, it will /// be used as a fall-back if no regular field or method are found. @@ -493,11 +483,6 @@ pub trait UserDataFields { /// Add a regular field getter as a function which accepts a generic [`AnyUserData`] of type `T` /// argument. - /// - /// Prefer to use [`add_field_method_get`] as it is easier to use. - /// - /// [`AnyUserData`]: crate::AnyUserData - /// [`add_field_method_get`]: #method.add_field_method_get fn add_field_function_get(&mut self, name: impl ToString, function: F) where F: Fn(&Lua, AnyUserData) -> Result + MaybeSend + 'static, @@ -505,11 +490,6 @@ pub trait UserDataFields { /// Add a regular field setter as a function which accepts a generic [`AnyUserData`] of type `T` /// first argument. - /// - /// Prefer to use [`add_field_method_set`] as it is easier to use. - /// - /// [`AnyUserData`]: crate::AnyUserData - /// [`add_field_method_set`]: #method.add_field_method_set fn add_field_function_set(&mut self, name: impl ToString, function: F) where F: FnMut(&Lua, AnyUserData, A) -> Result<()> + MaybeSend + 'static, @@ -517,7 +497,7 @@ pub trait UserDataFields { /// Add a metatable field. /// - /// This will initialize the metatable field with `value` on `UserData` creation. + /// This will initialize the metatable field with `value` on [`UserData`] creation. /// /// # Note /// @@ -529,7 +509,7 @@ pub trait UserDataFields { /// Add a metatable field computed from `f`. /// - /// This will initialize the metatable field from `f` on `UserData` creation. + /// This will initialize the metatable field from `f` on [`UserData`] creation. /// /// # Note /// @@ -544,6 +524,7 @@ pub trait UserDataFields { /// Trait for custom userdata types. /// /// By implementing this trait, a struct becomes eligible for use inside Lua code. +/// /// Implementation of [`IntoLua`] is automatically provided, [`FromLua`] needs to be implemented /// manually. /// @@ -603,11 +584,6 @@ pub trait UserDataFields { /// # Ok(()) /// # } /// ``` -/// -/// [`IntoLua`]: crate::IntoLua -/// [`FromLua`]: crate::FromLua -/// [`UserDataFields`]: crate::UserDataFields -/// [`UserDataMethods`]: crate::UserDataMethods pub trait UserData: Sized { /// Adds custom fields specific to this userdata. #[allow(unused_variables)] @@ -629,18 +605,14 @@ pub trait UserData: Sized { /// Handle to an internal Lua userdata for any type that implements [`UserData`]. /// -/// Similar to `std::any::Any`, this provides an interface for dynamic type checking via the [`is`] -/// and [`borrow`] methods. -/// -/// Internally, instances are stored in a `RefCell`, to best match the mutable semantics of the Lua -/// language. +/// Similar to [`std::any::Any`], this provides an interface for dynamic type checking via the +/// [`is`] and [`borrow`] methods. /// /// # Note /// /// This API should only be used when necessary. Implementing [`UserData`] already allows defining /// methods which check the type and acquire a borrow behind the scenes. /// -/// [`UserData`]: crate::UserData /// [`is`]: crate::AnyUserData::is /// [`borrow`]: crate::AnyUserData::borrow #[derive(Clone, Debug, PartialEq)] @@ -657,8 +629,12 @@ impl AnyUserData { /// /// # Errors /// - /// Returns a `UserDataBorrowError` if the userdata is already mutably borrowed. Returns a - /// `UserDataTypeMismatch` if the userdata is not of type `T` or if it's scoped. + /// Returns a [`UserDataBorrowError`] if the userdata is already mutably borrowed. + /// Returns a [`DataTypeMismatch`] if the userdata is not of type `T` or if it's + /// scoped. + /// + /// [`UserDataBorrowError`]: crate::Error::UserDataBorrowError + /// [`DataTypeMismatch`]: crate::Error::UserDataTypeMismatch #[inline] pub fn borrow(&self) -> Result> { self.inspect(|ud| ud.try_borrow_owned()) @@ -676,8 +652,12 @@ impl AnyUserData { /// /// # Errors /// - /// Returns a `UserDataBorrowMutError` if the userdata cannot be mutably borrowed. - /// Returns a `UserDataTypeMismatch` if the userdata is not of type `T` or if it's scoped. + /// Returns a [`UserDataBorrowMutError`] if the userdata cannot be mutably borrowed. + /// Returns a [`UserDataTypeMismatch`] if the userdata is not of type `T` or if it's + /// scoped. + /// + /// [`UserDataBorrowMutError`]: crate::Error::UserDataBorrowMutError + /// [`UserDataTypeMismatch`]: crate::Error::UserDataTypeMismatch #[inline] pub fn borrow_mut(&self) -> Result> { self.inspect(|ud| ud.try_borrow_owned_mut()) @@ -692,6 +672,7 @@ impl AnyUserData { } /// Takes the value out of this userdata. + /// /// Sets the special "destructed" metatable that prevents any further operations with this /// userdata. /// @@ -715,14 +696,14 @@ impl AnyUserData { } } - /// Sets an associated value to this `AnyUserData`. + /// Sets an associated value to this [`AnyUserData`]. /// /// The value may be any Lua value whatsoever, and can be retrieved with [`user_value`]. /// /// This is the same as calling [`set_nth_user_value`] with `n` set to 1. /// - /// [`user_value`]: #method.user_value - /// [`set_nth_user_value`]: #method.set_nth_user_value + /// [`user_value`]: AnyUserData::user_value + /// [`set_nth_user_value`]: AnyUserData::set_nth_user_value #[inline] pub fn set_user_value(&self, v: impl IntoLua) -> Result<()> { self.set_nth_user_value(1, v) @@ -732,23 +713,21 @@ impl AnyUserData { /// /// This is the same as calling [`nth_user_value`] with `n` set to 1. /// - /// [`set_user_value`]: #method.set_user_value - /// [`nth_user_value`]: #method.nth_user_value + /// [`set_user_value`]: AnyUserData::set_user_value + /// [`nth_user_value`]: AnyUserData::nth_user_value #[inline] pub fn user_value(&self) -> Result { self.nth_user_value(1) } - /// Sets an associated `n`th value to this `AnyUserData`. + /// Sets an associated `n`th value to this [`AnyUserData`]. /// /// The value may be any Lua value whatsoever, and can be retrieved with [`nth_user_value`]. /// `n` starts from 1 and can be up to 65535. /// - /// This is supported for all Lua versions. - /// In Lua 5.4 first 7 elements are stored in a most efficient way. - /// For other Lua versions this functionality is provided using a wrapping table. + /// This is supported for all Lua versions using a wrapping table. /// - /// [`nth_user_value`]: #method.nth_user_value + /// [`nth_user_value`]: AnyUserData::nth_user_value pub fn set_nth_user_value(&self, n: usize, v: impl IntoLua) -> Result<()> { if n < 1 || n > u16::MAX as usize { return Err(Error::runtime("user value index out of bounds")); @@ -784,11 +763,9 @@ impl AnyUserData { /// /// `n` starts from 1 and can be up to 65535. /// - /// This is supported for all Lua versions. - /// In Lua 5.4 first 7 elements are stored in a most efficient way. - /// For other Lua versions this functionality is provided using a wrapping table. + /// This is supported for all Lua versions using a wrapping table. /// - /// [`set_nth_user_value`]: #method.set_nth_user_value + /// [`set_nth_user_value`]: AnyUserData::set_nth_user_value pub fn nth_user_value(&self, n: usize) -> Result { if n < 1 || n > u16::MAX as usize { return Err(Error::runtime("user value index out of bounds")); @@ -812,11 +789,11 @@ impl AnyUserData { } } - /// Sets an associated value to this `AnyUserData` by name. + /// Sets an associated value to this [`AnyUserData`] by name. /// /// The value can be retrieved with [`named_user_value`]. /// - /// [`named_user_value`]: #method.named_user_value + /// [`named_user_value`]: AnyUserData::named_user_value pub fn set_named_user_value(&self, name: &str, v: impl IntoLua) -> Result<()> { let lua = self.0.lua.lock(); let state = lua.state(); @@ -847,7 +824,7 @@ impl AnyUserData { /// Returns an associated value by name set by [`set_named_user_value`]. /// - /// [`set_named_user_value`]: #method.set_named_user_value + /// [`set_named_user_value`]: AnyUserData::set_named_user_value pub fn named_user_value(&self, name: &str) -> Result { let lua = self.0.lua.lock(); let state = lua.state(); @@ -868,14 +845,12 @@ impl AnyUserData { } } - /// Returns a metatable of this `UserData`. + /// Returns a metatable of this [`AnyUserData`]. /// /// Returned [`UserDataMetatable`] object wraps the original metatable and /// provides safe access to its methods. /// /// For `T: 'static` returned metatable is shared among all instances of type `T`. - /// - /// [`UserDataMetatable`]: crate::UserDataMetatable #[inline] pub fn metatable(&self) -> Result { self.raw_metatable().map(UserDataMetatable) @@ -952,8 +927,8 @@ impl AnyUserData { Ok(false) } - /// Returns `true` if this `AnyUserData` is serializable (eg. was created using - /// `create_ser_userdata`). + /// Returns `true` if this [`AnyUserData`] is serializable (e.g. was created using + /// [`Lua::create_ser_userdata`]). #[cfg(feature = "serialize")] pub(crate) fn is_serializable(&self) -> bool { let lua = self.0.lua.lock(); @@ -985,7 +960,7 @@ impl AnyUserData { } } -/// Handle to a `UserData` metatable. +/// Handle to a [`AnyUserData`] metatable. #[derive(Clone, Debug)] pub struct UserDataMetatable(pub(crate) Table); @@ -1028,14 +1003,11 @@ impl UserDataMetatable { } } -/// An iterator over the pairs of a [`UserData`] metatable. +/// An iterator over the pairs of a [`AnyUserData`] metatable. /// /// It skips restricted metamethods, such as `__gc` or `__metatable`. /// /// This struct is created by the [`UserDataMetatable::pairs`] method. -/// -/// [`UserData`]: crate::UserData -/// [`UserDataMetatable::pairs`]: crate::UserDataMetatable::method.pairs pub struct UserDataMetatablePairs<'a, V>(TablePairs<'a, StdString, V>); impl Iterator for UserDataMetatablePairs<'_, V> @@ -1081,7 +1053,7 @@ pub(crate) struct WrappedUserdata Result>(F); impl AnyUserData { /// Wraps any Rust type, returning an opaque type that implements [`IntoLua`] trait. /// - /// This function uses [`Lua::create_any_userdata()`] under the hood. + /// This function uses [`Lua::create_any_userdata`] under the hood. pub fn wrap(data: T) -> impl IntoLua { WrappedUserdata(move |lua| lua.create_any_userdata(data)) } @@ -1089,7 +1061,7 @@ impl AnyUserData { /// Wraps any Rust type that implements [`Serialize`], returning an opaque type that implements /// [`IntoLua`] trait. /// - /// This function uses [`Lua::create_ser_any_userdata()`] under the hood. + /// This function uses [`Lua::create_ser_any_userdata`] under the hood. #[cfg(feature = "serialize")] #[cfg_attr(docsrs, doc(cfg(feature = "serialize")))] pub fn wrap_ser(data: T) -> impl IntoLua { diff --git a/src/userdata/cell.rs b/src/userdata/cell.rs index c48ae2f..fe3a019 100644 --- a/src/userdata/cell.rs +++ b/src/userdata/cell.rs @@ -145,7 +145,7 @@ impl UserDataCell { } } -/// A wrapper type for a [`UserData`] value that provides read access. +/// A wrapper type for a userdata value that provides read access. /// /// It implements [`FromLua`] and can be used to receive a typed userdata from Lua. pub struct UserDataRef(UserDataVariant); @@ -206,7 +206,7 @@ impl FromLua for UserDataRef { } } -/// A wrapper type for a mutably borrowed value from a `AnyUserData`. +/// A wrapper type for a userdata value that provides read and write access. /// /// It implements [`FromLua`] and can be used to receive a typed userdata from Lua. pub struct UserDataRefMut(UserDataVariant); diff --git a/src/value.rs b/src/value.rs index f84829d..6c81ee5 100644 --- a/src/value.rs +++ b/src/value.rs @@ -104,10 +104,10 @@ impl Value { /// Compares two values for equality. /// /// Equality comparisons do not convert strings to numbers or vice versa. - /// Tables, Functions, Threads, and UserData are compared by reference: + /// Tables, functions, threads, and userdata are compared by reference: /// two objects are considered equal only if they are the same object. /// - /// If Tables or UserData have `__eq` metamethod then mlua will try to invoke it. + /// If table or userdata have `__eq` metamethod then mlua will try to invoke it. /// The first value is checked first. If that value does not define a metamethod /// for `__eq`, then mlua will check the second value. /// Then mlua calls the metamethod with the two values as arguments, if found. @@ -193,6 +193,8 @@ impl Value { } /// Returns `true` if the value is a [`NULL`]. + /// + /// [`NULL`]: Value::NULL #[inline] pub fn is_null(&self) -> bool { self == &Self::NULL @@ -433,9 +435,11 @@ impl Value { } } - /// Cast the value to a `Buffer`. + /// Cast the value to a [`Buffer`]. /// - /// If the value is `Buffer`, returns it or `None` otherwise. + /// If the value is [`Buffer`], returns it or `None` otherwise. + /// + /// [`Buffer`]: crate::Buffer #[cfg(any(feature = "luau", doc))] #[cfg_attr(docsrs, doc(cfg(feature = "luau")))] #[inline] @@ -446,7 +450,9 @@ impl Value { } } - /// Returns `true` if the value is a `Buffer`. + /// Returns `true` if the value is a [`Buffer`]. + /// + /// [`Buffer`]: crate::Buffer #[cfg(any(feature = "luau", doc))] #[cfg_attr(docsrs, doc(cfg(feature = "luau")))] #[inline]