1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
|
// Copyright © 2017 Mozilla Foundation
//
// This program is made available under an ISC-style license. See the
// accompanying file LICENSE for details.
#![warn(unused_extern_crates)]
#[macro_use]
extern crate log;
#[macro_use]
mod send_recv;
mod context;
mod stream;
use crate::context::ClientContext;
use crate::stream::ClientStream;
use audioipc::PlatformHandleType;
use cubeb_backend::{capi, ffi};
use std::os::raw::{c_char, c_int};
thread_local!(static IN_CALLBACK: std::cell::RefCell<bool> = std::cell::RefCell::new(false));
thread_local!(static AUDIOIPC_INIT_PARAMS: std::cell::RefCell<Option<AudioIpcInitParams>> = std::cell::RefCell::new(None));
#[repr(C)]
#[derive(Clone, Copy, Debug)]
pub struct AudioIpcInitParams {
// Fields only need to be public for ipctest.
pub server_connection: PlatformHandleType,
pub pool_size: usize,
pub stack_size: usize,
pub thread_create_callback: Option<extern "C" fn(*const ::std::os::raw::c_char)>,
pub thread_destroy_callback: Option<extern "C" fn()>,
}
unsafe impl Send for AudioIpcInitParams {}
fn set_in_callback(in_callback: bool) {
IN_CALLBACK.with(|b| {
assert_eq!(*b.borrow(), !in_callback);
*b.borrow_mut() = in_callback;
});
}
fn run_in_callback<F, R>(f: F) -> R
where
F: FnOnce() -> R,
{
set_in_callback(true);
let r = f();
set_in_callback(false);
r
}
fn assert_not_in_callback() {
IN_CALLBACK.with(|b| {
assert!(!*b.borrow());
});
}
#[allow(clippy::missing_safety_doc)]
#[no_mangle]
/// Entry point from C code.
pub unsafe extern "C" fn audioipc2_client_init(
c: *mut *mut ffi::cubeb,
context_name: *const c_char,
init_params: *const AudioIpcInitParams,
) -> c_int {
if init_params.is_null() {
return cubeb_backend::ffi::CUBEB_ERROR;
}
let init_params = &*init_params;
AUDIOIPC_INIT_PARAMS.with(|p| {
*p.borrow_mut() = Some(*init_params);
});
capi::capi_init::<ClientContext>(c, context_name)
}
|