use crate::raw;
use super::super::Error;
use super::Library;
use super::api::SymBorApi;
use std::ffi::OsStr;
use std::mem::transmute;
use std::ops::{Deref, DerefMut};
pub struct Container<T>
where
T: SymBorApi<'static>,
{
#[allow(dead_code)]
lib: Library,
api: T,
}
impl<T> Container<T>
where
T: SymBorApi<'static>,
{
pub unsafe fn load<S>(name: S) -> Result<Self, Error>
where
S: AsRef<OsStr>,
{
unsafe {
let lib = Library::open(name)?;
let static_ref: &'static Library = transmute(&lib);
let api = T::load(static_ref)?;
Ok(Self { api, lib })
}
}
pub unsafe fn load_self() -> Result<Self, Error> {
unsafe {
let lib = Library::open_self()?;
let static_ref: &'static Library = transmute(&lib);
let api = T::load(static_ref)?;
Ok(Self { api, lib })
}
}
pub unsafe fn into_raw(&self) -> raw::Handle {
unsafe { self.lib.into_raw() }
}
}
impl<T> Deref for Container<T>
where
T: SymBorApi<'static>,
{
type Target = T;
fn deref(&self) -> &T {
&self.api
}
}
impl<T> DerefMut for Container<T>
where
T: SymBorApi<'static>,
{
fn deref_mut(&mut self) -> &mut T {
&mut self.api
}
}