mirror of
https://gitee.com/openharmony/third_party_rust_cxx
synced 2025-02-21 09:03:31 +00:00
Support shared_ptr of primitives
This commit is contained in:
parent
1cde514d94
commit
5b16340b67
44
src/cxx.cc
44
src/cxx.cc
@ -331,6 +331,15 @@ Error &Error::operator=(Error &&other) noexcept {
|
||||
|
||||
const char *Error::what() const noexcept { return this->msg; }
|
||||
|
||||
namespace {
|
||||
template <typename T>
|
||||
union MaybeUninit {
|
||||
T value;
|
||||
MaybeUninit() {}
|
||||
~MaybeUninit() {}
|
||||
};
|
||||
} // namespace
|
||||
|
||||
} // namespace cxxbridge1
|
||||
} // namespace rust
|
||||
|
||||
@ -443,6 +452,34 @@ static_assert(sizeof(std::string) <= kMaxExpectedWordsInString * sizeof(void *),
|
||||
return cxxbridge1$rust_vec$##RUST_TYPE##$stride(); \
|
||||
}
|
||||
|
||||
#define SHARED_PTR_OPS(RUST_TYPE, CXX_TYPE) \
|
||||
static_assert(sizeof(std::shared_ptr<CXX_TYPE>) == 2 * sizeof(void *), ""); \
|
||||
static_assert(alignof(std::shared_ptr<CXX_TYPE>) == alignof(void *), ""); \
|
||||
void cxxbridge1$std$shared_ptr$##RUST_TYPE##$null( \
|
||||
std::shared_ptr<CXX_TYPE> *ptr) noexcept { \
|
||||
new (ptr) std::shared_ptr<CXX_TYPE>(); \
|
||||
} \
|
||||
CXX_TYPE *cxxbridge1$std$shared_ptr$##RUST_TYPE##$uninit( \
|
||||
std::shared_ptr<CXX_TYPE> *ptr) noexcept { \
|
||||
CXX_TYPE *uninit = \
|
||||
reinterpret_cast<CXX_TYPE *>(new rust::MaybeUninit<CXX_TYPE>); \
|
||||
new (ptr) std::shared_ptr<CXX_TYPE>(uninit); \
|
||||
return uninit; \
|
||||
} \
|
||||
void cxxbridge1$std$shared_ptr$##RUST_TYPE##$clone( \
|
||||
const std::shared_ptr<CXX_TYPE> &self, \
|
||||
std::shared_ptr<CXX_TYPE> *ptr) noexcept { \
|
||||
new (ptr) std::shared_ptr<CXX_TYPE>(self); \
|
||||
} \
|
||||
const CXX_TYPE *cxxbridge1$std$shared_ptr$##RUST_TYPE##$get( \
|
||||
const std::shared_ptr<CXX_TYPE> &self) noexcept { \
|
||||
return self.get(); \
|
||||
} \
|
||||
void cxxbridge1$std$shared_ptr$##RUST_TYPE##$drop( \
|
||||
const std::shared_ptr<CXX_TYPE> *self) noexcept { \
|
||||
self->~shared_ptr(); \
|
||||
}
|
||||
|
||||
// Usize and isize are the same type as one of the below.
|
||||
#define FOR_EACH_NUMERIC(MACRO) \
|
||||
MACRO(u8, uint8_t) \
|
||||
@ -468,9 +505,16 @@ static_assert(sizeof(std::string) <= kMaxExpectedWordsInString * sizeof(void *),
|
||||
MACRO(char, char) \
|
||||
MACRO(string, rust::String)
|
||||
|
||||
#define FOR_EACH_SHARED_PTR(MACRO) \
|
||||
FOR_EACH_NUMERIC(MACRO) \
|
||||
MACRO(usize, size_t) \
|
||||
MACRO(isize, rust::isize) \
|
||||
MACRO(string, std::string)
|
||||
|
||||
extern "C" {
|
||||
FOR_EACH_STD_VECTOR(STD_VECTOR_OPS)
|
||||
FOR_EACH_RUST_VEC(RUST_VEC_EXTERNS)
|
||||
FOR_EACH_SHARED_PTR(SHARED_PTR_OPS)
|
||||
} // extern "C"
|
||||
|
||||
namespace rust {
|
||||
|
@ -1,3 +1,4 @@
|
||||
use crate::cxx_string::CxxString;
|
||||
use crate::kind::Trivial;
|
||||
use crate::ExternType;
|
||||
use core::ffi::c_void;
|
||||
@ -189,3 +190,77 @@ pub unsafe trait SharedPtrTarget {
|
||||
#[doc(hidden)]
|
||||
unsafe fn __drop(this: *mut c_void);
|
||||
}
|
||||
|
||||
macro_rules! impl_shared_ptr_target {
|
||||
($segment:expr, $name:expr, $ty:ty) => {
|
||||
unsafe impl SharedPtrTarget for $ty {
|
||||
const __NAME: &'static dyn Display = &$name;
|
||||
unsafe fn __null(new: *mut c_void) {
|
||||
extern "C" {
|
||||
attr! {
|
||||
#[link_name = concat!("cxxbridge1$std$shared_ptr$", $segment, "$null")]
|
||||
fn __null(new: *mut c_void);
|
||||
}
|
||||
}
|
||||
__null(new);
|
||||
}
|
||||
unsafe fn __new(value: Self, new: *mut c_void) {
|
||||
extern "C" {
|
||||
attr! {
|
||||
#[link_name = concat!("cxxbridge1$std$shared_ptr$", $segment, "$uninit")]
|
||||
fn __uninit(new: *mut c_void) -> *mut c_void;
|
||||
}
|
||||
}
|
||||
__uninit(new).cast::<$ty>().write(value);
|
||||
}
|
||||
unsafe fn __clone(this: *const c_void, new: *mut c_void) {
|
||||
extern "C" {
|
||||
attr! {
|
||||
#[link_name = concat!("cxxbridge1$std$shared_ptr$", $segment, "$clone")]
|
||||
fn __clone(this: *const c_void, new: *mut c_void);
|
||||
}
|
||||
}
|
||||
__clone(this, new);
|
||||
}
|
||||
unsafe fn __get(this: *const c_void) -> *const Self {
|
||||
extern "C" {
|
||||
attr! {
|
||||
#[link_name = concat!("cxxbridge1$std$shared_ptr$", $segment, "$get")]
|
||||
fn __get(this: *const c_void) -> *const c_void;
|
||||
}
|
||||
}
|
||||
__get(this).cast()
|
||||
}
|
||||
unsafe fn __drop(this: *mut c_void) {
|
||||
extern "C" {
|
||||
attr! {
|
||||
#[link_name = concat!("cxxbridge1$std$shared_ptr$", $segment, "$drop")]
|
||||
fn __drop(this: *mut c_void);
|
||||
}
|
||||
}
|
||||
__drop(this);
|
||||
}
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
macro_rules! impl_shared_ptr_target_for_primitive {
|
||||
($ty:ident) => {
|
||||
impl_shared_ptr_target!(stringify!($ty), stringify!($ty), $ty);
|
||||
};
|
||||
}
|
||||
|
||||
impl_shared_ptr_target_for_primitive!(u8);
|
||||
impl_shared_ptr_target_for_primitive!(u16);
|
||||
impl_shared_ptr_target_for_primitive!(u32);
|
||||
impl_shared_ptr_target_for_primitive!(u64);
|
||||
impl_shared_ptr_target_for_primitive!(usize);
|
||||
impl_shared_ptr_target_for_primitive!(i8);
|
||||
impl_shared_ptr_target_for_primitive!(i16);
|
||||
impl_shared_ptr_target_for_primitive!(i32);
|
||||
impl_shared_ptr_target_for_primitive!(i64);
|
||||
impl_shared_ptr_target_for_primitive!(isize);
|
||||
impl_shared_ptr_target_for_primitive!(f32);
|
||||
impl_shared_ptr_target_for_primitive!(f64);
|
||||
|
||||
impl_shared_ptr_target!("string", "CxxString", CxxString);
|
||||
|
Loading…
x
Reference in New Issue
Block a user