Clippy fixes and documentation
All checks were successful
continuous-integration/drone/push Build is passing
All checks were successful
continuous-integration/drone/push Build is passing
This commit is contained in:
@@ -75,26 +75,31 @@ extern "C" fn pokemon_display_form(handle: FFIHandle<Pokemon>) -> FFIHandle<Arc<
|
||||
FFIHandle::get_handle(handle.from_ffi_handle().display_form().into())
|
||||
}
|
||||
|
||||
/// The level of the Pokemon.
|
||||
#[no_mangle]
|
||||
extern "C" fn pokemon_level(handle: FFIHandle<Pokemon>) -> LevelInt {
|
||||
handle.from_ffi_handle().level()
|
||||
}
|
||||
|
||||
/// The experience of the Pokemon.
|
||||
#[no_mangle]
|
||||
extern "C" fn pokemon_experience(handle: FFIHandle<Pokemon>) -> u32 {
|
||||
handle.from_ffi_handle().experience()
|
||||
}
|
||||
|
||||
/// The unique identifier of the Pokemon.
|
||||
#[no_mangle]
|
||||
extern "C" fn pokemon_unique_identifier(handle: FFIHandle<Pokemon>) -> u32 {
|
||||
handle.from_ffi_handle().unique_identifier()
|
||||
}
|
||||
|
||||
/// The gender of the Pokemon.
|
||||
#[no_mangle]
|
||||
extern "C" fn pokemon_gender(handle: FFIHandle<Pokemon>) -> Gender {
|
||||
handle.from_ffi_handle().gender()
|
||||
}
|
||||
|
||||
/// The coloring of the Pokemon.
|
||||
#[no_mangle]
|
||||
extern "C" fn pokemon_coloring(handle: FFIHandle<Pokemon>) -> u8 {
|
||||
handle.from_ffi_handle().coloring()
|
||||
@@ -149,21 +154,25 @@ extern "C" fn pokemon_consume_held_item(handle: FFIHandle<Pokemon>) -> FFIResult
|
||||
}
|
||||
}
|
||||
|
||||
/// The current health of the Pokemon.
|
||||
#[no_mangle]
|
||||
extern "C" fn pokemon_current_health(handle: FFIHandle<Pokemon>) -> u32 {
|
||||
handle.from_ffi_handle().current_health()
|
||||
}
|
||||
|
||||
/// The max health of the Pokemon.
|
||||
#[no_mangle]
|
||||
extern "C" fn pokemon_max_health(handle: FFIHandle<Pokemon>) -> u32 {
|
||||
handle.from_ffi_handle().max_health()
|
||||
}
|
||||
|
||||
/// The current weight of the Pokemon.
|
||||
#[no_mangle]
|
||||
extern "C" fn pokemon_weight(handle: FFIHandle<Pokemon>) -> f32 {
|
||||
handle.from_ffi_handle().weight()
|
||||
}
|
||||
|
||||
/// The current height of the Pokemon.
|
||||
#[no_mangle]
|
||||
extern "C" fn pokemon_height(handle: FFIHandle<Pokemon>) -> f32 {
|
||||
handle.from_ffi_handle().height()
|
||||
@@ -196,11 +205,13 @@ extern "C" fn pokemon_real_ability_index(handle: FFIHandle<Pokemon>) -> u8 {
|
||||
handle.from_ffi_handle().real_ability().index
|
||||
}
|
||||
|
||||
/// The amount of types the Pokemon has.
|
||||
#[no_mangle]
|
||||
extern "C" fn pokemon_types_length(ptr: FFIHandle<Pokemon>) -> usize {
|
||||
ptr.from_ffi_handle().types().len()
|
||||
}
|
||||
|
||||
/// Gets a type of the Pokemon.
|
||||
#[no_mangle]
|
||||
extern "C" fn pokemon_types_get(ptr: FFIHandle<Pokemon>, index: usize) -> FFIResult<TypeIdentifier> {
|
||||
match ptr.from_ffi_handle().types().get_res(index) {
|
||||
|
||||
@@ -9,9 +9,14 @@ use std::hash::Hash;
|
||||
use std::sync::atomic::AtomicUsize;
|
||||
use std::sync::{Arc, LazyLock};
|
||||
|
||||
/// A handle of an object that can be passed over FFI. We use this to avoid passing pointers over the
|
||||
/// FFI boundary. This allows us to be able to move the data around in memory without having to worry
|
||||
/// about the pointers being invalidated. It also allows us to have a type-safe interface.
|
||||
#[repr(C)]
|
||||
pub(super) struct FFIHandle<T> {
|
||||
/// An incrementing handle that is unique for each object.
|
||||
handle: usize,
|
||||
/// The type of the object.
|
||||
_marker: std::marker::PhantomData<T>,
|
||||
}
|
||||
|
||||
@@ -26,7 +31,10 @@ impl<T> Clone for FFIHandle<T> {
|
||||
|
||||
impl<T> Copy for FFIHandle<T> {}
|
||||
|
||||
/// An FFIObject we can fetch from the FFIHandle. We store this in a hashmap to be able to fetch
|
||||
/// the object from the handle, and to be able to drop the object when the FFI is done with the handle
|
||||
#[derive(Clone)]
|
||||
#[allow(clippy::missing_docs_in_private_items)] // I'm not documenting these items.
|
||||
pub(super) enum FFIObject {
|
||||
Ability(Arc<dyn Ability>),
|
||||
EffectParameter(Arc<EffectParameter>),
|
||||
@@ -75,11 +83,15 @@ unsafe impl Send for FFIObject {}
|
||||
|
||||
unsafe impl Sync for FFIObject {}
|
||||
|
||||
/// The next handle to be used.
|
||||
static NEXT_HANDLE: AtomicUsize = AtomicUsize::new(0);
|
||||
/// A lookup to get an actual object from a handle.
|
||||
static FFI_OBJECTS: LazyLock<RwLock<HashMap<usize, FFIObject>>> = LazyLock::new(|| RwLock::new(HashMap::new()));
|
||||
/// A lookup to get a handle from an object.
|
||||
static FFI_OBJECTS_INVERSE: LazyLock<RwLock<HashMap<FFIObject, usize>>> = LazyLock::new(|| RwLock::new(HashMap::new()));
|
||||
|
||||
impl<T> FFIHandle<T> {
|
||||
/// Get a handle from an object.
|
||||
pub fn get_handle(o: FFIObject) -> Self {
|
||||
if let Some(handle) = FFI_OBJECTS_INVERSE.read().get(&o) {
|
||||
return Self {
|
||||
@@ -97,6 +109,7 @@ impl<T> FFIHandle<T> {
|
||||
}
|
||||
}
|
||||
|
||||
/// An empty handle. This is used when no value is returned. Represented as handle 0
|
||||
pub fn none() -> Self {
|
||||
Self {
|
||||
handle: 0,
|
||||
@@ -104,6 +117,7 @@ impl<T> FFIHandle<T> {
|
||||
}
|
||||
}
|
||||
|
||||
/// Get the object from the handle.
|
||||
#[allow(clippy::unwrap_used)] // Unwrap used, as it is a potential security bug if this fails
|
||||
pub fn resolve(&self) -> FFIObject {
|
||||
FFI_OBJECTS
|
||||
@@ -114,6 +128,7 @@ impl<T> FFIHandle<T> {
|
||||
.clone()
|
||||
}
|
||||
|
||||
/// Check if the handle is empty.
|
||||
pub fn is_none(&self) -> bool {
|
||||
self.handle == 0
|
||||
}
|
||||
@@ -132,9 +147,12 @@ impl<T> Into<anyhow_ext::Result<FFIObject>> for FFIHandle<T> {
|
||||
|
||||
impl Eq for FFIObject {}
|
||||
|
||||
/// A trait to convert a handle into an object.
|
||||
#[allow(clippy::wrong_self_convention)]
|
||||
pub(super) trait FromFFIHandle<T> {
|
||||
/// Convert a handle into an object.
|
||||
fn from_ffi_handle(&self) -> T;
|
||||
/// Convert a handle into an object, returning `None` if the handle is empty.
|
||||
fn from_ffi_handle_opt(&self) -> Option<T>;
|
||||
}
|
||||
|
||||
@@ -229,6 +247,8 @@ impl PartialEq for FFIObject {
|
||||
}
|
||||
}
|
||||
|
||||
/// Helper macro to implement the `From` trait for a `FFIObject` enum variant, and the `FromFFIHandle`
|
||||
/// trait for a `FFIHandle` enum variant.
|
||||
macro_rules! ffi_obj_conversions {
|
||||
($res_type:ty, $ffi_obj_name:ident) => {
|
||||
impl From<$res_type> for FFIObject {
|
||||
|
||||
@@ -1,5 +1,6 @@
|
||||
/// The foreign function interfaces for the dynamic data
|
||||
mod dynamic_data;
|
||||
/// The handling of handles for the foreign function interfaces
|
||||
mod ffi_handle;
|
||||
/// The foreign function interfaces for that static data
|
||||
mod static_data;
|
||||
|
||||
Reference in New Issue
Block a user