From d951cb503f7d1c8e006f90c0954eb8e6bdbc3c92 Mon Sep 17 00:00:00 2001 From: Alex Orlenko Date: Sat, 6 May 2023 22:53:40 +0100 Subject: [PATCH] Add `Value::NULL` constant --- src/serde/mod.rs | 4 +--- src/value.rs | 6 ++++++ tests/value.rs | 3 +++ 3 files changed, 10 insertions(+), 3 deletions(-) diff --git a/src/serde/mod.rs b/src/serde/mod.rs index a4328df..8b83c21 100644 --- a/src/serde/mod.rs +++ b/src/serde/mod.rs @@ -1,7 +1,6 @@ //! (De)Serialization support using serde. use std::os::raw::c_void; -use std::ptr; use serde::{Deserialize, Serialize}; @@ -9,7 +8,6 @@ use crate::error::Result; use crate::lua::Lua; use crate::private::Sealed; use crate::table::Table; -use crate::types::LightUserData; use crate::util::check_stack; use crate::value::Value; @@ -200,7 +198,7 @@ pub trait LuaSerdeExt<'lua>: Sealed { impl<'lua> LuaSerdeExt<'lua> for Lua { fn null(&'lua self) -> Value<'lua> { - Value::LightUserData(LightUserData(ptr::null_mut())) + Value::NULL } fn array_metatable(&'lua self) -> Table<'lua> { diff --git a/src/value.rs b/src/value.rs index 74834a9..2678e4b 100644 --- a/src/value.rs +++ b/src/value.rs @@ -63,6 +63,12 @@ pub enum Value<'lua> { pub use self::Value::Nil; impl<'lua> Value<'lua> { + /// A special value (lightuserdata) to represent null value. + /// + /// It can be used in Lua tables without downsides of `nil`. + pub const NULL: Value<'static> = Value::LightUserData(LightUserData(ptr::null_mut())); + + /// Returns type name of this value. pub const fn type_name(&self) -> &'static str { match *self { Value::Nil => "nil", diff --git a/tests/value.rs b/tests/value.rs index f318387..439a490 100644 --- a/tests/value.rs +++ b/tests/value.rs @@ -28,6 +28,7 @@ fn test_value_eq() -> Result<()> { "#, ) .exec()?; + globals.set("null", Value::NULL)?; let table1: Value = globals.get("table1")?; let table2: Value = globals.get("table2")?; @@ -41,6 +42,7 @@ fn test_value_eq() -> Result<()> { let func3: Value = globals.get("func3")?; let thread1: Value = globals.get("thread1")?; let thread2: Value = globals.get("thread2")?; + let null: Value = globals.get("null")?; assert!(table1 != table2); assert!(table1.equals(&table2)?); @@ -54,6 +56,7 @@ fn test_value_eq() -> Result<()> { assert!(!func1.equals(&func3)?); assert!(thread1 == thread2); assert!(thread1.equals(&thread2)?); + assert!(null == Value::NULL); assert!(!table1.to_pointer().is_null()); assert!(!ptr::eq(table1.to_pointer(), table2.to_pointer()));