Repository: RustPython/RustPython
File: crates/vm/src/stdlib/ctypes.rs (Rust)

Code before:
        let (id, _) = cache_write.get_or_insert_lib(&name, vm).unwrap();
        Ok(id)
    }

    #[pyfunction(name = "dlopen")]
    fn load_library_unix(
        name: Option<String>,
        _load_flags: OptionalArg<i32>,
        vm: &VirtualMachine,
    ) -> PyResult<usize> {
        // TODO: audit functions first
        // TODO: load_flags
        match name {
            Some(name) => {
                let cache = library::libcache();
                let mut cache_write = cache.write();
                let (id, _) = cache_write
                    .get_or_insert_lib(&name, vm)
                    .map_err(|e| vm.new_os_error(e.to_string()))?;
                Ok(id)
            }
            None => {
                // If None, call libc::dlopen(null, mode) to get the current process handle
                let handle = unsafe { libc::dlopen(std::ptr::null(), libc::RTLD_NOW) };
                if handle.is_null() {
                    return Err(vm.new_os_error("dlopen() error".to_string()));
                }
                Ok(handle as usize)
            }
        }
    }

    #[pyfunction(name = "FreeLibrary")]
    fn free_library(handle: usize) -> PyResult<()> {
        let cache = library::libcache();
        let mut cache_write = cache.write();
        cache_write.drop_lib(handle);
        Ok(())
    }

    #[pyfunction(name = "POINTER")]
    pub fn create_pointer_type(cls: PyObjectRef, vm: &VirtualMachine) -> PyResult {
        // Get the _pointer_type_cache
        let ctypes_module = vm.import("_ctypes", 0)?;
        let cache = ctypes_module.get_attr("_pointer_type_cache", vm)?;

        // Check if already in cache using __getitem__
        if let Ok(cached) = vm.call_method(&cache, "__getitem__", (cls.clone(),)) {
            if !vm.is_none(&cached) {
                return Ok(cached);
            }

Review comment (suggestion):
```suggestion
                    return Err(vm.new_os_error("dlopen() error"));
```

Code after:
        _load_flags: OptionalArg<i32>,
        vm: &VirtualMachine,
    ) -> PyResult<usize> {
        // TODO: audit functions first
        // TODO: load_flags
        let cache = library::libcache();
        let mut cache_write = cache.write();
        let (id, _) = cache_write.get_or_insert_lib(&name, vm).unwrap();
        Ok(id)
    }

    #[cfg(not(windows))]
    #[pyfunction(name = "dlopen")]
    fn load_library_unix(
        name: Option<String>,
        _load_flags: OptionalArg<i32>,
        vm: &VirtualMachine,
    ) -> PyResult<usize> {
        // TODO: audit functions first
        // TODO: load_flags
        match name {
            Some(name) => {
                let cache = library::libcache();
                let mut cache_write = cache.write();
                let (id, _) = cache_write
                    .get_or_insert_lib(&name, vm)
                    .map_err(|e| vm.new_os_error(e.to_string()))?;
                Ok(id)
            }
            None => {
                // If None, call libc::dlopen(null, mode) to get the current process handle
                let handle = unsafe { libc::dlopen(std::ptr::null(), libc::RTLD_NOW) };
                if handle.is_null() {
                    return Err(vm.new_os_error("dlopen() error"));
                }
                Ok(handle as usize)
            }
        }
    }

    #[pyfunction(name = "FreeLibrary")]
    fn free_library(handle: usize) -> PyResult<()> {
        let cache = library::libcache();
        let mut cache_write = cache.write();
        cache_write.drop_lib(handle);
        Ok(())
    }

    #[pyfunction(name = "POINTER")]
    pub fn create_pointer_type(cls: PyObjectRef, vm: &VirtualMachine) -> PyResult {
        // Get the _pointer_type_cache