Skip to content

Commit

Permalink
argconv: pointers
Browse files Browse the repository at this point in the history
This commit introduces a `CassPtr` type, generic over
pointer `Properties`. It allows specific pointer-to-reference conversions
based on the guarantees provided by the pointer type.

Existing `Ref/Box/Arc`FFIs are adjusted, so they now allow
interaction with new pointer type. You can say, that for a user of
`argconv` API, new type is opaque. The only way to operate on it is to
use the corresponding ffi API.
  • Loading branch information
muzarski committed Dec 12, 2024
1 parent 95299d2 commit f0492eb
Show file tree
Hide file tree
Showing 22 changed files with 1,559 additions and 1,059 deletions.
369 changes: 326 additions & 43 deletions scylla-rust-wrapper/src/argconv.rs

Large diffs are not rendered by default.

48 changes: 24 additions & 24 deletions scylla-rust-wrapper/src/batch.rs
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
use crate::argconv::{ArcFFI, BoxFFI};
use crate::argconv::{ArcFFI, BoxFFI, CassExclusiveConstPtr, CassExclusiveMutPtr, CassSharedPtr};
use crate::cass_error::CassError;
use crate::cass_types::CassConsistency;
use crate::cass_types::{make_batch_type, CassBatchType};
Expand Down Expand Up @@ -28,7 +28,7 @@ pub struct CassBatchState {
}

#[no_mangle]
pub unsafe extern "C" fn cass_batch_new(type_: CassBatchType) -> *mut CassBatch {
pub unsafe extern "C" fn cass_batch_new(type_: CassBatchType) -> CassExclusiveMutPtr<CassBatch> {
if let Some(batch_type) = make_batch_type(type_) {
BoxFFI::into_ptr(Box::new(CassBatch {
state: Arc::new(CassBatchState {
Expand All @@ -39,21 +39,21 @@ pub unsafe extern "C" fn cass_batch_new(type_: CassBatchType) -> *mut CassBatch
exec_profile: None,
}))
} else {
std::ptr::null_mut()
BoxFFI::null_mut()
}
}

#[no_mangle]
pub unsafe extern "C" fn cass_batch_free(batch: *mut CassBatch) {
pub unsafe extern "C" fn cass_batch_free(batch: CassExclusiveMutPtr<CassBatch>) {
BoxFFI::free(batch);
}

#[no_mangle]
pub unsafe extern "C" fn cass_batch_set_consistency(
batch: *mut CassBatch,
mut batch: CassExclusiveMutPtr<CassBatch>,
consistency: CassConsistency,
) -> CassError {
let batch = BoxFFI::as_mut_ref(batch);
let batch = BoxFFI::as_mut_ref(&mut batch).unwrap();
let consistency = match consistency.try_into().ok() {
Some(c) => c,
None => return CassError::CASS_ERROR_LIB_BAD_PARAMS,
Expand All @@ -67,10 +67,10 @@ pub unsafe extern "C" fn cass_batch_set_consistency(

#[no_mangle]
pub unsafe extern "C" fn cass_batch_set_serial_consistency(
batch: *mut CassBatch,
mut batch: CassExclusiveMutPtr<CassBatch>,
serial_consistency: CassConsistency,
) -> CassError {
let batch = BoxFFI::as_mut_ref(batch);
let batch = BoxFFI::as_mut_ref(&mut batch).unwrap();
let serial_consistency = match serial_consistency.try_into().ok() {
Some(c) => c,
None => return CassError::CASS_ERROR_LIB_BAD_PARAMS,
Expand All @@ -84,13 +84,13 @@ pub unsafe extern "C" fn cass_batch_set_serial_consistency(

#[no_mangle]
pub unsafe extern "C" fn cass_batch_set_retry_policy(
batch: *mut CassBatch,
retry_policy: *const CassRetryPolicy,
mut batch: CassExclusiveMutPtr<CassBatch>,
retry_policy: CassSharedPtr<CassRetryPolicy>,
) -> CassError {
let batch = BoxFFI::as_mut_ref(batch);
let batch = BoxFFI::as_mut_ref(&mut batch).unwrap();

let maybe_arced_retry_policy: Option<Arc<dyn scylla::retry_policy::RetryPolicy>> =
ArcFFI::as_maybe_ref(retry_policy).map(|policy| match policy {
ArcFFI::as_ref(&retry_policy).map(|policy| match policy {
CassRetryPolicy::DefaultRetryPolicy(default) => {
default.clone() as Arc<dyn scylla::retry_policy::RetryPolicy>
}
Expand All @@ -107,10 +107,10 @@ pub unsafe extern "C" fn cass_batch_set_retry_policy(

#[no_mangle]
pub unsafe extern "C" fn cass_batch_set_timestamp(
batch: *mut CassBatch,
mut batch: CassExclusiveMutPtr<CassBatch>,
timestamp: cass_int64_t,
) -> CassError {
let batch = BoxFFI::as_mut_ref(batch);
let batch = BoxFFI::as_mut_ref(&mut batch).unwrap();

Arc::make_mut(&mut batch.state)
.batch
Expand All @@ -121,21 +121,21 @@ pub unsafe extern "C" fn cass_batch_set_timestamp(

#[no_mangle]
pub unsafe extern "C" fn cass_batch_set_request_timeout(
batch: *mut CassBatch,
mut batch: CassExclusiveMutPtr<CassBatch>,
timeout_ms: cass_uint64_t,
) -> CassError {
let batch = BoxFFI::as_mut_ref(batch);
let batch = BoxFFI::as_mut_ref(&mut batch).unwrap();
batch.batch_request_timeout_ms = Some(timeout_ms);

CassError::CASS_OK
}

#[no_mangle]
pub unsafe extern "C" fn cass_batch_set_is_idempotent(
batch: *mut CassBatch,
mut batch: CassExclusiveMutPtr<CassBatch>,
is_idempotent: cass_bool_t,
) -> CassError {
let batch = BoxFFI::as_mut_ref(batch);
let batch = BoxFFI::as_mut_ref(&mut batch).unwrap();
Arc::make_mut(&mut batch.state)
.batch
.set_is_idempotent(is_idempotent != 0);
Expand All @@ -145,10 +145,10 @@ pub unsafe extern "C" fn cass_batch_set_is_idempotent(

#[no_mangle]
pub unsafe extern "C" fn cass_batch_set_tracing(
batch: *mut CassBatch,
mut batch: CassExclusiveMutPtr<CassBatch>,
enabled: cass_bool_t,
) -> CassError {
let batch = BoxFFI::as_mut_ref(batch);
let batch = BoxFFI::as_mut_ref(&mut batch).unwrap();
Arc::make_mut(&mut batch.state)
.batch
.set_tracing(enabled != 0);
Expand All @@ -158,12 +158,12 @@ pub unsafe extern "C" fn cass_batch_set_tracing(

#[no_mangle]
pub unsafe extern "C" fn cass_batch_add_statement(
batch: *mut CassBatch,
statement: *const CassStatement,
mut batch: CassExclusiveMutPtr<CassBatch>,
statement: CassExclusiveConstPtr<CassStatement>,
) -> CassError {
let batch = BoxFFI::as_mut_ref(batch);
let batch = BoxFFI::as_mut_ref(&mut batch).unwrap();
let state = Arc::make_mut(&mut batch.state);
let statement = BoxFFI::as_ref(statement);
let statement = BoxFFI::as_ref(&statement).unwrap();

match &statement.statement {
BoundStatement::Simple(q) => {
Expand Down
34 changes: 18 additions & 16 deletions scylla-rust-wrapper/src/binding.rs
Original file line number Diff line number Diff line change
Expand Up @@ -53,15 +53,15 @@ macro_rules! make_index_binder {
#[no_mangle]
#[allow(clippy::redundant_closure_call)]
pub unsafe extern "C" fn $fn_by_idx(
this: *mut $this,
mut this: CassExclusiveMutPtr<$this>,
index: size_t,
$($arg: $t), *
) -> CassError {
// For some reason detected as unused, which is not true
#[allow(unused_imports)]
use crate::value::CassCqlValue::*;
match ($e)($($arg), *) {
Ok(v) => $consume_v(BoxFFI::as_mut_ref(this), index as usize, v),
Ok(v) => $consume_v(BoxFFI::as_mut_ref(&mut this).unwrap(), index as usize, v),
Err(e) => e,
}
}
Expand All @@ -73,7 +73,7 @@ macro_rules! make_name_binder {
#[no_mangle]
#[allow(clippy::redundant_closure_call)]
pub unsafe extern "C" fn $fn_by_name(
this: *mut $this,
mut this: CassExclusiveMutPtr<$this>,
name: *const c_char,
$($arg: $t), *
) -> CassError {
Expand All @@ -82,7 +82,7 @@ macro_rules! make_name_binder {
use crate::value::CassCqlValue::*;
let name = ptr_to_cstr(name).unwrap();
match ($e)($($arg), *) {
Ok(v) => $consume_v(BoxFFI::as_mut_ref(this), name, v),
Ok(v) => $consume_v(BoxFFI::as_mut_ref(&mut this).unwrap(), name, v),
Err(e) => e,
}
}
Expand All @@ -94,7 +94,7 @@ macro_rules! make_name_n_binder {
#[no_mangle]
#[allow(clippy::redundant_closure_call)]
pub unsafe extern "C" fn $fn_by_name_n(
this: *mut $this,
mut this: CassExclusiveMutPtr<$this>,
name: *const c_char,
name_length: size_t,
$($arg: $t), *
Expand All @@ -104,7 +104,7 @@ macro_rules! make_name_n_binder {
use crate::value::CassCqlValue::*;
let name = ptr_to_cstr_n(name, name_length).unwrap();
match ($e)($($arg), *) {
Ok(v) => $consume_v(BoxFFI::as_mut_ref(this), name, v),
Ok(v) => $consume_v(BoxFFI::as_mut_ref(&mut this).unwrap(), name, v),
Err(e) => e,
}
}
Expand All @@ -116,14 +116,14 @@ macro_rules! make_appender {
#[no_mangle]
#[allow(clippy::redundant_closure_call)]
pub unsafe extern "C" fn $fn_append(
this: *mut $this,
mut this: CassExclusiveMutPtr<$this>,
$($arg: $t), *
) -> CassError {
// For some reason detected as unused, which is not true
#[allow(unused_imports)]
use crate::value::CassCqlValue::*;
match ($e)($($arg), *) {
Ok(v) => $consume_v(BoxFFI::as_mut_ref(this), v),
Ok(v) => $consume_v(BoxFFI::as_mut_ref(&mut this).unwrap(), v),
Err(e) => e,
}
}
Expand Down Expand Up @@ -302,33 +302,35 @@ macro_rules! invoke_binder_maker_macro_with_type {
$this,
$consume_v,
$fn,
|p: *const crate::collection::CassCollection| {
match std::convert::TryInto::try_into(BoxFFI::as_ref(p)) {
|p: CassExclusiveConstPtr<crate::collection::CassCollection>| {
match std::convert::TryInto::try_into(BoxFFI::as_ref(&p).unwrap()) {
Ok(v) => Ok(Some(v)),
Err(_) => Err(CassError::CASS_ERROR_LIB_INVALID_VALUE_TYPE),
}
},
[p @ *const crate::collection::CassCollection]
[p @ CassExclusiveConstPtr<crate::collection::CassCollection>]
);
};
(tuple, $macro_name:ident, $this:ty, $consume_v:expr, $fn:ident) => {
$macro_name!(
$this,
$consume_v,
$fn,
|p: *const crate::tuple::CassTuple| {
Ok(Some(BoxFFI::as_ref(p).into()))
|p: CassExclusiveConstPtr<crate::tuple::CassTuple>| {
Ok(Some(BoxFFI::as_ref(&p).unwrap().into()))
},
[p @ *const crate::tuple::CassTuple]
[p @ CassExclusiveConstPtr<crate::tuple::CassTuple>]
);
};
(user_type, $macro_name:ident, $this:ty, $consume_v:expr, $fn:ident) => {
$macro_name!(
$this,
$consume_v,
$fn,
|p: *const crate::user_type::CassUserType| Ok(Some(BoxFFI::as_ref(p).into())),
[p @ *const crate::user_type::CassUserType]
|p: CassExclusiveConstPtr<crate::user_type::CassUserType>| {
Ok(Some(BoxFFI::as_ref(&p).unwrap().into()))
},
[p @ CassExclusiveConstPtr<crate::user_type::CassUserType>]
);
};
}
Expand Down
Loading

0 comments on commit f0492eb

Please sign in to comment.