From 67512cbe58d321694fa361b4f09ee725cf1619e5 Mon Sep 17 00:00:00 2001 From: Anhad Singh Date: Tue, 14 Jul 2026 17:41:27 +1000 Subject: [PATCH] feat(ld.so): remove ObjectHandle ld.so has been merged with libc.so Signed-off-by: Anhad Singh --- src/header/dlfcn/mod.rs | 16 ++++++---- src/ld_so/linker.rs | 65 ++++++++--------------------------------- src/ld_so/mod.rs | 2 +- 3 files changed, 23 insertions(+), 60 deletions(-) diff --git a/src/header/dlfcn/mod.rs b/src/header/dlfcn/mod.rs index d1ca5c0470..eeab93f7f5 100644 --- a/src/header/dlfcn/mod.rs +++ b/src/header/dlfcn/mod.rs @@ -11,10 +11,13 @@ use core::{ sync::atomic::{AtomicUsize, Ordering}, }; +use alloc::sync::Arc; + use crate::{ c_str::CStr, ld_so::{ - linker::{DlError, ObjectHandle, Resolve, ScopeKind}, + dso::DSO, + linker::{DlError, Resolve, ScopeKind}, tcb::Tcb, }, platform::types::{c_char, c_int, c_void}, @@ -124,7 +127,7 @@ pub unsafe extern "C" fn dlopen(cfilename: *const c_char, flags: c_int) -> *mut let mut linker = unsafe { (*tcb.linker_ptr).lock() }; match linker.load_library(filename, resolve, scope, noload) { - Ok(handle) => handle.as_ptr().cast_mut(), + Ok(handle) => Arc::into_raw(handle).cast::().cast_mut(), Err(error) => { set_last_error(error); ptr::null_mut() @@ -135,7 +138,7 @@ pub unsafe extern "C" fn dlopen(cfilename: *const c_char, flags: c_int) -> *mut /// See . #[unsafe(no_mangle)] pub unsafe extern "C" fn dlsym(handle: *mut c_void, symbol: *const c_char) -> *mut c_void { - let handle = ObjectHandle::from_ptr(handle); + let handle = unsafe { handle.cast::().as_ref() }; if symbol.is_null() { ERROR.store(ERROR_NOT_SUPPORTED.as_ptr() as usize, Ordering::SeqCst); @@ -181,13 +184,14 @@ pub unsafe extern "C" fn dlclose(handle: *mut c_void) -> c_int { return -1; }; - let Some(handle) = ObjectHandle::from_ptr(handle) else { + if handle.is_null() { set_last_error(DlError::InvalidHandle); return -1; - }; + } let mut linker = unsafe { (*tcb.linker_ptr).lock() }; - linker.unload(handle); + let obj = unsafe { Arc::from_raw(handle.cast::()) }; + linker.unload(obj); 0 } diff --git a/src/ld_so/linker.rs b/src/ld_so/linker.rs index fdd0b51123..dd3a18505a 100644 --- a/src/ld_so/linker.rs +++ b/src/ld_so/linker.rs @@ -11,7 +11,7 @@ use object::{ read::elf::{Rela as _, Sym}, }; -use core::ptr::{self, NonNull}; +use core::ptr; use crate::{ ALLOCATOR, @@ -323,41 +323,6 @@ impl Scope { } } -// Used by dlfcn.h -// -// We need this as the handle must be created and destroyed with the dynamic -// linker's allocator. -pub struct ObjectHandle(*const DSO); - -impl ObjectHandle { - #[inline] - fn new(obj: Arc) -> Self { - Self(Arc::into_raw(obj)) - } - - #[inline] - fn into_inner(self) -> Arc { - unsafe { Arc::from_raw(self.0) } - } - - #[inline] - pub fn as_ptr(&self) -> *const c_void { - self.0.cast() - } - - #[inline] - pub fn from_ptr(ptr: *const c_void) -> Option { - NonNull::new(ptr as *mut DSO).map(|ptr| Self(ptr.as_ptr())) - } -} - -impl AsRef for ObjectHandle { - #[inline] - fn as_ref(&self) -> &DSO { - unsafe { &*self.0 } - } -} - bitflags::bitflags! { #[derive(Debug, Default)] pub struct DebugFlags: u32 { @@ -467,7 +432,7 @@ impl Linker { resolve: Resolve, scope: ScopeKind, noload: bool, - ) -> Result { + ) -> Result> { log::trace!( "[ld.so] load_library(name={:?}, resolve={:#?}, scope={:#?}, noload={})", name, @@ -502,14 +467,14 @@ impl Linker { self.scope_debug(); } - Ok(ObjectHandle::new(obj.clone())) + Ok(obj.clone()) } else if !noload { let parent_runpath = &self .objects .get(&ROOT_ID) .and_then(|parent| parent.runpath().cloned()); - Ok(ObjectHandle::new(self.load_object( + Ok(self.load_object( name, parent_runpath, None, @@ -520,29 +485,24 @@ impl Linker { resolve }, scope, - )?)) + )?) } else { - // FIXME: LoadError? - // Err(Error::Malformed(format!( - // "object '{}' has not yet been loaded", - // name - // ))) - Ok(ObjectHandle(ptr::null())) + Err(DlError::NotFound) } } None => match self.objects.get(&ROOT_ID) { - Some(obj) => Ok(ObjectHandle::new(obj.clone())), + Some(obj) => Ok(obj.clone()), None => Err(DlError::NotFound), }, } } - pub fn get_sym(&self, handle: Option, name: &str) -> Option<*mut c_void> { + pub fn get_sym(&self, handle: Option<&DSO>, name: &str) -> Option<*mut c_void> { let guard; - if let Some(handle) = handle.as_ref() { - handle.as_ref().scope() + if let Some(handle) = handle { + handle.scope() } else { guard = GLOBAL_SCOPE.read(); &guard @@ -562,8 +522,7 @@ impl Linker { }) } - pub fn unload(&mut self, handle: ObjectHandle) { - let obj = handle.into_inner(); + pub fn unload(&mut self, obj: Arc) { if !obj.dlopened { return; } @@ -592,7 +551,7 @@ impl Linker { if let Some(name) = self.name_to_object_id_map.get(*dep) && let Some(object_name) = self.objects.get(name) { - self.unload(ObjectHandle::new(object_name.clone())); + self.unload(object_name.clone()); } } self.name_to_object_id_map.remove(&obj.name); diff --git a/src/ld_so/mod.rs b/src/ld_so/mod.rs index 43d6b96787..0bf42bf182 100644 --- a/src/ld_so/mod.rs +++ b/src/ld_so/mod.rs @@ -22,7 +22,7 @@ pub const PATH_SEP: char = ':'; mod access; pub mod debug; -mod dso; +pub mod dso; pub mod linker; pub mod start; pub mod tcb;