From 19a337dc37dfea32a0fe509007a756d54d596855 Mon Sep 17 00:00:00 2001 From: jmjoy Date: Thu, 19 Jun 2025 20:46:13 +0800 Subject: [PATCH 1/2] feat: Add raw pointer casting methods for EBox --- phper/src/alloc.rs | 22 ++++++++++++++++++++++ phper/src/arrays.rs | 6 +++--- phper/src/classes.rs | 8 +++----- phper/src/objects.rs | 4 ++-- phper/src/strings.rs | 8 ++++---- phper/src/values.rs | 4 ++-- 6 files changed, 36 insertions(+), 16 deletions(-) diff --git a/phper/src/alloc.rs b/phper/src/alloc.rs index f6bb4da..b89c570 100644 --- a/phper/src/alloc.rs +++ b/phper/src/alloc.rs @@ -37,12 +37,34 @@ impl EBox { Self { ptr: raw } } + /// Constructs from a raw pointer with cast. + /// + /// # Safety + /// + /// Make sure the pointer is from `into_raw`, or created from `emalloc`. + pub(crate) unsafe fn from_raw_cast(raw: *mut U) -> Self { + const { + assert!(size_of::() == size_of::()); + } + Self { ptr: raw.cast() } + } + /// Consumes and returning a wrapped raw pointer. /// /// Will leak memory. pub fn into_raw(b: EBox) -> *mut T { ManuallyDrop::new(b).ptr } + + /// Consumes and returning a wrapped raw pointer with cast. + /// + /// Will leak memory. + pub(crate) fn into_raw_cast(b: EBox) -> *mut U { + const { + assert!(size_of::() == size_of::()); + } + ManuallyDrop::new(b).ptr.cast() + } } impl fmt::Debug for EBox { diff --git a/phper/src/arrays.rs b/phper/src/arrays.rs index 0d19787..b017e61 100644 --- a/phper/src/arrays.rs +++ b/phper/src/arrays.rs @@ -356,7 +356,7 @@ impl ToOwned for ZArr { unsafe { // TODO The source really immutable? let dest = phper_zend_array_dup(self.as_ptr() as *mut _); - ZArray::from_raw(dest.cast()) + ZArray::from_raw_cast(dest) } } } @@ -369,7 +369,7 @@ impl ToRefOwned for ZArr { unsafe { phper_zval_arr(val.as_mut_ptr(), self.as_mut_ptr()); phper_z_addref_p(val.as_mut_ptr()); - ZArray::from_raw(val.as_mut_z_arr().unwrap().as_mut_ptr().cast()) + ZArray::from_raw_cast(val.as_mut_z_arr().unwrap().as_mut_ptr()) } } } @@ -395,7 +395,7 @@ impl ZArray { pub fn with_capacity(n: usize) -> Self { unsafe { let ptr = phper_zend_new_array(n.try_into().unwrap()); - Self::from_raw(ptr.cast()) + Self::from_raw_cast(ptr) } } } diff --git a/phper/src/classes.rs b/phper/src/classes.rs index 694c8a6..3e1cd29 100644 --- a/phper/src/classes.rs +++ b/phper/src/classes.rs @@ -147,7 +147,7 @@ impl ClassEntry { // day of debugging time here). let mut val = ManuallyDrop::new(val); let ptr = phper_z_obj_p(val.as_mut_ptr()); - Ok(ZObject::from_raw(ptr.cast())) + Ok(ZObject::from_raw_cast(ptr)) } } } @@ -334,8 +334,7 @@ impl StateClass { pub fn new_object(&self, arguments: impl AsMut<[ZVal]>) -> crate::Result> { self.as_class_entry() .new_object(arguments) - .map(ZObject::into_raw) - .map(|ptr| ptr.cast()) + .map(ZObject::into_raw_cast) .map(StateObject::::from_raw_object) } @@ -345,8 +344,7 @@ impl StateClass { pub fn init_object(&self) -> crate::Result> { self.as_class_entry() .init_object() - .map(ZObject::into_raw) - .map(|ptr| ptr.cast()) + .map(ZObject::into_raw_cast) .map(StateObject::::from_raw_object) } } diff --git a/phper/src/objects.rs b/phper/src/objects.rs index 4cd6bcc..5263d14 100644 --- a/phper/src/objects.rs +++ b/phper/src/objects.rs @@ -282,7 +282,7 @@ impl ToRefOwned for ZObj { unsafe { phper_zval_obj(val.as_mut_ptr(), self.as_mut_ptr()); phper_z_addref_p(val.as_mut_ptr()); - ZObject::from_raw(val.as_mut_z_obj().unwrap().as_mut_ptr().cast()) + ZObject::from_raw_cast(val.as_mut_z_obj().unwrap().as_mut_ptr()) } } } @@ -447,7 +447,7 @@ impl StateObject { /// Converts into [ZObject]. pub fn into_z_object(self) -> ZObject { - unsafe { ZObject::from_raw(self.into_raw_object().cast()) } + unsafe { ZObject::from_raw_cast(self.into_raw_object()) } } } diff --git a/phper/src/strings.rs b/phper/src/strings.rs index 62d73ab..6b8a370 100644 --- a/phper/src/strings.rs +++ b/phper/src/strings.rs @@ -175,7 +175,7 @@ impl ToRefOwned for ZStr { fn to_ref_owned(&mut self) -> Self::Owned { unsafe { let ptr = phper_zend_string_copy(self.as_mut_ptr()); - ZString::from_raw(ptr.cast()) + ZString::from_raw_cast(ptr) } } } @@ -198,7 +198,7 @@ impl ZString { s.len().try_into().unwrap(), false.into(), ); - Self::from_raw(ptr.cast()) + Self::from_raw_cast(ptr) } } @@ -209,7 +209,7 @@ impl ZString { let s = s.as_ref(); let ptr = phper_zend_string_init(s.as_ptr().cast(), s.len().try_into().unwrap(), true.into()); - Self::from_raw(ptr.cast()) + Self::from_raw_cast(ptr) } } } @@ -222,7 +222,7 @@ impl Clone for ZString { phper_zstr_len(self.as_ptr()).try_into().unwrap(), false.into(), ); - Self::from_raw(ZStr::from_mut_ptr(ptr.cast())) + Self::from_raw_cast(ZStr::from_mut_ptr(ptr)) } } } diff --git a/phper/src/values.rs b/phper/src/values.rs index d41f19a..8fa32df 100644 --- a/phper/src/values.rs +++ b/phper/src/values.rs @@ -736,7 +736,7 @@ impl From for ZVal { fn from(s: ZString) -> Self { unsafe { let mut val = MaybeUninit::::uninit(); - phper_zval_str(val.as_mut_ptr().cast(), ZString::into_raw(s).cast()); + phper_zval_str(val.as_mut_ptr().cast(), ZString::into_raw_cast(s)); val.assume_init() } } @@ -746,7 +746,7 @@ impl From for ZVal { fn from(arr: ZArray) -> Self { unsafe { let mut val = MaybeUninit::::uninit(); - phper_zval_arr(val.as_mut_ptr().cast(), ZArray::into_raw(arr).cast()); + phper_zval_arr(val.as_mut_ptr().cast(), ZArray::into_raw_cast(arr)); val.assume_init() } } From 1a74be9c60caacc78ec76301b57f2d824539448f Mon Sep 17 00:00:00 2001 From: jmjoy Date: Thu, 19 Jun 2025 20:47:49 +0800 Subject: [PATCH 2/2] Continue --- phper/src/functions.rs | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/phper/src/functions.rs b/phper/src/functions.rs index 0ab1119..4bf4cca 100644 --- a/phper/src/functions.rs +++ b/phper/src/functions.rs @@ -651,7 +651,7 @@ impl ZFunc { pub fn get_function_or_method_name(&self) -> ZString { unsafe { let s = phper_get_function_or_method_name(self.as_ptr()); - ZString::from_raw(s.cast()) + ZString::from_raw_cast(s) } } @@ -890,7 +890,7 @@ pub(crate) fn call_raw_common(call_fn: impl FnOnce(&mut ZVal)) -> crate::Result< if !eg!(exception).is_null() { #[allow(static_mut_refs)] let e = ptr::replace(&mut eg!(exception), null_mut()); - let obj = ZObject::from_raw(e.cast()); + let obj = ZObject::from_raw_cast(e); match ThrowObject::new(obj) { Ok(e) => return Err(e.into()), Err(e) => return Err(e.into()),