#[path = "base.s.r-type.rs"]
pub mod r_type;
use r_type::{RType, RTypeMut, RDefault, RTypeFrom, error, alias::*, SEXPext, SEXP, SEXPTYPE};
#[cfg(not(have_std))]
use {r_type::print, crate::String};
#[cfg(doc)]
use r_type::define::*; pub mod macros {
pub macro impl_sext_index (SExt=$SExt:tt SEXP=$SEXP:tt RType=$RType:tt RTypeMut=$RTypeMut:tt Mutable=$Mutable:tt,$($tt:tt)*) {
use core::ops::{Index,IndexMut};
$(
impl<T: $RType> $SExt for $tt<T> {
type Data = T;
unsafe fn as_sexp(&self) -> $SEXP {
self.sexp
}
}
impl<T: $RType> Index<usize> for $tt<T> where $tt<T>:$SExt {
type Output = <<$tt<T> as $SExt>::Data as $RType>::Data;
fn index(&self, index: usize) -> &<<$tt<T> as $SExt>::Data as $RType>::Data {
self.data().index(index)
}
}
impl<T: $RTypeMut> IndexMut<usize> for $tt<T> where $tt<T>:$Mutable, <$tt<T> as $SExt>::Data:$RTypeMut {
fn index_mut(&mut self, index: usize) -> &mut <<$tt<T> as $SExt>::Data as $RType>::Data {
self.data_mut().index_mut(index)
}
}
)*
}
}
use macros::impl_sext_index;
use core::marker::PhantomData;
#[derive(Copy, Clone)]
#[repr(transparent)]
pub struct Sexp<T: RType> {
sexp: SEXP,
_marker: [PhantomData<T>; 0],
}
#[repr(transparent)]
pub struct Owned<T: RType> {
sexp: SEXP,
_marker: [PhantomData<T>; 0],
}
impl<T: RType> Owned<T> {
pub fn protect(self) -> Protected<T> {
self.into()
}
}
#[repr(transparent)]
pub struct Protected<T: RType> {
sexp: SEXP,
_marker: [PhantomData<T>; 0],
}
pub trait SExt: Sized {
type Data: RType;
unsafe fn as_sexp(&self) -> SEXP;
fn stype(&self)->SEXPTYPE {
unsafe {self.as_sexp().stype()}
}
fn new(len: usize) -> Protected<Self::Data>
where
Self::Data: RDefault,
{
Protected::<Self::Data> {
sexp: unsafe {<Self::Data as RType>::new(len).protect()},
_marker: [],
}
.into()
}
fn raw(len: usize) -> Owned<Self::Data>
where
Self::Data: RDefault,
{
Owned::<Self::Data> {
sexp: unsafe {<Self::Data as RType>::new(len)},
_marker: [],
}
}
fn from(data: impl core::convert::AsRef<[<Self::Data as RType>::Data]>) -> Protected<Self::Data>
where
Self::Data: RTypeFrom,
{
Protected::<Self::Data> {
sexp: unsafe {<Self::Data as RType>::from(data)},
_marker: [],
}
.into()
}
fn raw_from(data: impl core::convert::AsRef<[<Self::Data as RType>::Data]>) -> Owned<Self::Data>
where
Self::Data: RTypeFrom,
{
Owned::<Self::Data> {
sexp: unsafe {<Self::Data as RType>::from(data)},
_marker: [],
}
}
#[inline(always)]
fn is_correct_type(&self) -> bool {
self.stype() == Self::Data::SEXPTYPE
}
#[inline(always)]
fn len(&self) -> usize {
unsafe {self.as_sexp().len() as usize}
}
#[inline(always)]
unsafe fn data_unchecked(&self) -> &[<Self::Data as RType>::Data] {
unsafe { core::slice::from_raw_parts(Self::Data::data(self.as_sexp()), self.len()) }
}
#[inline(always)]
fn data(&self) -> &[<Self::Data as RType>::Data] {
if self.len() == 0 {
&[]
} else {
if self.is_correct_type() {
unsafe { self.data_unchecked() }
} else {
panic!(
"data has the type {}, but {}(={}) is required.",
self.stype(),
core::any::type_name::<<Self::Data as RType>::Data>(),
<Self::Data as RType>::SEXPTYPE,
)
}
}
}
#[inline(always)]
unsafe fn data_unchecked_mut(&self) -> &mut [<Self::Data as RType>::Data]
where
<Self as SExt>::Data: RTypeMut,
Self: Mutable,
{
unsafe { core::slice::from_raw_parts_mut(Self::Data::data_mut(self.as_sexp()), self.len()) }
}
#[inline(always)]
fn data_mut(&mut self) -> &mut [<Self::Data as RType>::Data]
where
<Self as SExt>::Data: RTypeMut,
Self: Mutable,
{
if self.len() == 0 {
&mut []
} else {
if self.is_correct_type() {
unsafe { self.data_unchecked_mut() }
} else {
panic!(
"data has the type {}, but {}(={}) is required.",
self.stype(),
core::any::type_name::<Self::Data>(),
<Self::Data as RType>::SEXPTYPE,
)
}
}
}
}
impl<T:RType> Sexp<T> {
#[inline(always)]
pub fn missing(&self) -> bool { self.missingness() != 0
}
#[inline(always)]
pub fn missingness(&self) -> i32 { unsafe {self.as_sexp().missing() as i32}
}
}
pub trait Mutable {}
impl<T: RTypeMut> Mutable for Owned<T> {}
impl<T: RTypeMut> Mutable for Protected<T> {}
impl<T: RType> From<Owned<T>> for Protected<T> {
#[inline(always)]
fn from(s: Owned<T>) -> Self {
Self {
sexp: unsafe { s.sexp.protect() },
_marker: [],
}
}
}
impl<T: RType> From<Protected<T>> for Owned<T> {
#[inline(always)]
fn from(s: Protected<T>) -> Self {
Self {
sexp: s.sexp,
_marker: [],
}
}
}
impl<T: RType> From<Protected<T>> for Sexp<T> {
#[inline(always)]
fn from(s: Protected<T>) -> Self {
Self {
sexp: s.sexp,
_marker: [],
}
}
}
impl<T: RType> From<Owned<T>> for Sexp<T> {
#[inline(always)]
fn from(s: Owned<T>) -> Self {
Self {
sexp: s.sexp,
_marker: [],
}
}
}
impl<T: RType> Drop for Protected<T> {
#[inline(always)]
fn drop(&mut self) {
unsafe { self.sexp.unprotect() }
}
}
unsafe impl Sync for Sexp<Rchar> {}
unsafe impl Send for Sexp<Rchar> {}
impl Sexp<Rchar> {
pub unsafe fn error(self)->!{
unsafe {error(Rchar::data(self.as_sexp()))}
}
#[cfg_attr(doc, doc(cfg(not(have_std))))]
#[cfg(not(have_std))]
pub fn print(self){
unsafe {print(Rchar::data(self.as_sexp()))}
}
}
impl Owned<character> {
pub fn raw_from_str(a:impl Into<String>)->Self{
Self::raw_from([<Owned<Rchar> as Into<Sexp<Rchar>>>::into(Owned::raw_from(a.into()))])
}
#[deprecated(since = "0.0.0", note = "Please use `raw_from_str` to ensure you are generate a `raw Owned` rather than `normal protected` type.")]
pub fn from_str(a:impl Into<String>)->Self{
Self::raw_from_str(a)
}
}
impl_sext_index! {SExt=SExt SEXP=SEXP RType=RType RTypeMut=RTypeMut Mutable=Mutable, Sexp Owned Protected}