use std::ptr::NonNull;
use crate::error::{Result, SpanDspError};
use crate::t30::T30State;
use crate::t38_core::{T38Core, T38TerminalOptions};
pub struct T38Terminal {
inner: NonNull<spandsp_sys::t38_terminal_state_t>,
}
impl T38Terminal {
pub unsafe fn new_raw(
calling_party: bool,
tx_packet_handler: spandsp_sys::t38_tx_packet_handler_t,
tx_packet_user_data: *mut std::ffi::c_void,
) -> Result<Self> {
unsafe {
let ptr = spandsp_sys::t38_terminal_init(
std::ptr::null_mut(),
calling_party,
tx_packet_handler,
tx_packet_user_data,
);
let inner = NonNull::new(ptr).ok_or(SpanDspError::InitFailed)?;
Ok(Self { inner })
}
}
pub fn as_ptr(&self) -> *mut spandsp_sys::t38_terminal_state_t {
self.inner.as_ptr()
}
pub fn get_t30_state(&self) -> Result<T30State> {
let ptr = unsafe { spandsp_sys::t38_terminal_get_t30_state(self.inner.as_ptr()) };
unsafe { T30State::from_raw(ptr, false) }
}
pub fn get_t38_core_state(&self) -> Result<T38Core> {
let ptr = unsafe { spandsp_sys::t38_terminal_get_t38_core_state(self.inner.as_ptr()) };
unsafe { T38Core::from_raw(ptr) }
}
pub fn send_timeout(&self, samples: i32) -> i32 {
unsafe { spandsp_sys::t38_terminal_send_timeout(self.inner.as_ptr(), samples) }
}
pub fn set_config(&self, config: T38TerminalOptions) {
unsafe {
spandsp_sys::t38_terminal_set_config(self.inner.as_ptr(), config.bits());
}
}
pub fn set_tep_mode(&self, use_tep: bool) {
unsafe {
spandsp_sys::t38_terminal_set_tep_mode(self.inner.as_ptr(), use_tep);
}
}
pub fn set_fill_bit_removal(&self, remove: bool) {
unsafe {
spandsp_sys::t38_terminal_set_fill_bit_removal(self.inner.as_ptr(), remove);
}
}
pub fn restart(&self, calling_party: bool) -> Result<()> {
let rc = unsafe { spandsp_sys::t38_terminal_restart(self.inner.as_ptr(), calling_party) };
if rc != 0 {
return Err(SpanDspError::ErrorCode(rc));
}
Ok(())
}
}
unsafe impl Send for T38Terminal {}
impl Drop for T38Terminal {
fn drop(&mut self) {
unsafe {
spandsp_sys::t38_terminal_free(self.inner.as_ptr());
}
}
}