From 4d9c4f84efa5fe4063c4522f233415d7ab18d774 Mon Sep 17 00:00:00 2001 From: Will Date: Thu, 12 Sep 2024 08:21:32 -0700 Subject: [PATCH] Log before JACK library calls commence. (#208) * Enable jack logging sooner. - Make `log` crate an optional dependency. - Write documentation for available features. * Bump version. --- .github/workflows/linting.yml | 4 +- Cargo.toml | 10 +-- docs/features.md | 46 ++++++++++++++ docs/logging.md | 49 +++++++++++++++ docs/quickstart.md | 1 + examples/playback_capture.rs | 17 ++++-- examples/sine.rs | 4 +- src/client/async_client.rs | 4 +- src/client/client_impl.rs | 40 ++---------- src/client/test_callback.rs | 20 ++++-- src/lib.rs | 24 ++------ src/logging.rs | 111 ++++++++++++++++++++++++++++++++++ src/port/audio.rs | 16 +++-- src/port/test_client.rs | 67 +++++++++++--------- src/port/test_port.rs | 26 +++++--- 15 files changed, 322 insertions(+), 117 deletions(-) create mode 100644 docs/features.md create mode 100644 docs/logging.md create mode 100644 src/logging.rs diff --git a/.github/workflows/linting.yml b/.github/workflows/linting.yml index a1d244ecc..64ddc8366 100644 --- a/.github/workflows/linting.yml +++ b/.github/workflows/linting.yml @@ -15,9 +15,9 @@ jobs: - name: Checkout uses: actions/checkout@v2 - name: Install dependencies - run: sudo apt update && sudo apt install jackd libjack0 libjack-dev + run: sudo apt update && sudo apt install jackd2 libjack-jackd2-0 libjack-jackd2-dev - name: Lint (No Features) - run: cargo clippy --all-targets --no-default-features -- -D clippy::all + run: cargo clippy --all-targets -- -D clippy::all - name: Lint (metadata) run: cargo clippy --all-targets --no-default-features --features metadata -- -D clippy::all - name: Cargo Fmt diff --git a/Cargo.toml b/Cargo.toml index 86c6508b6..954a8f1be 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -8,19 +8,19 @@ license = "MIT" name = "jack" readme = "README.md" repository = "https://github.com/RustAudio/rust-jack" -version = "0.12.1" +version = "0.12.2" [dependencies] bitflags = "2" jack-sys = {version = "0.5", path = "./jack-sys"} lazy_static = "1.4" libc = "0.2" -log = "0.4" +log = { version = "0.4", optional = true} [dev-dependencies] crossbeam-channel = "0.5" [features] -default = ["dynamic_loading"] -metadata = [] -dynamic_loading = ["jack-sys/dynamic_loading"] \ No newline at end of file +default = ["dynamic_loading", "log"] +dynamic_loading = ["jack-sys/dynamic_loading"] +metadata = [] \ No newline at end of file diff --git a/docs/features.md b/docs/features.md new file mode 100644 index 000000000..bbfb2d9b3 --- /dev/null +++ b/docs/features.md @@ -0,0 +1,46 @@ +--- +layout: page +title: Features +permalink: /features +nav_order: 1 +--- + +# Features + +The Rust features for the `jack` crate are defined in +. To see the +documentation for Rust features in general, see the [Rust +Book](https://doc.rust-lang.org/cargo/reference/features.html). + +## Disabling Default Features + +The `jack` crate ships with a reasonable set of default features. To enable just +a subset of features, set `default-features` to false and select only the +desired features. + +```toml +jack = { version = "..", default-features = false, features = ["log"] } +``` + +## `log` + +Default: Yes + +If the [`log` crate](https://crates.io/crates/log) should be used to handle JACK +logging. Requires setting up a logging implementation to make messages +available. + +## `dynamic_loading` + +Default: Yes + +Load `libjack` at runtime as opposed to the standard dynamic linking. This is +preferred as it allows `pw-jack` to intercept the loading at runtime to provide +the Pipewire JACK server implementation. + +## `metadata` + +Default: No + +Provides access to the metadata API. This is experimental. Details on the JACK +metadata API can be found at . diff --git a/docs/logging.md b/docs/logging.md new file mode 100644 index 000000000..cb1ee19b8 --- /dev/null +++ b/docs/logging.md @@ -0,0 +1,49 @@ +--- +layout: page +title: Logging +permalink: /logging +nav_order: 2 +--- + +# Logging + +JACK can communicate info and error messages. By default, the [log +crate](https://github.com/rust-lang/log) is hooked up to output +messages. However, other logging methods can be used with the +[`set_logger`](https://docs.rs/jack/latest/jack/fn.set_logger.html) function. + +## No Logging + +Logging from `jack` can be disabled entirely by setting the logger to `None`. + +```rust +jack::set_logger(jack::LoggerType::None); +``` + +## Log Crate (default) + +The log crate is the default logger if the `log` feature is enabled, which is +enabled by default. The `log` crate provides a *facade* for logging; it provides +macros to perform logging, but another mechanism or crate is required to +actually perform the logging. + +In the example below, we use the [`env_logger` crate]() to display logging for +info and error severity level messages. + +```rust +env_logger::builder().filter(None, log::LevelFilter::Info).init(); + +// JACK may log things to `info!` or `error!`. +let (client, _status) = + jack::Client::new("rust_jack_simple", jack::ClientOptions::NO_START_SERVER).unwrap(); +``` + + +## Stdio + +If the `log` feature is not enabled, then `jack` will log info messages to +`stdout` and error messages to `stderr`. These usually show up in the terminal. + +```rust +jack::set_logger(jack::LoggerType::Stdio); +``` diff --git a/docs/quickstart.md b/docs/quickstart.md index a210f918e..f66676c32 100644 --- a/docs/quickstart.md +++ b/docs/quickstart.md @@ -2,6 +2,7 @@ layout: page title: Quickstart permalink: / +nav_order: 0 --- # Quickstart diff --git a/examples/playback_capture.rs b/examples/playback_capture.rs index e070df9ad..528154a9d 100644 --- a/examples/playback_capture.rs +++ b/examples/playback_capture.rs @@ -4,15 +4,24 @@ use std::io; fn main() { // Create client + jack::set_logger(jack::LoggerType::Stdio); let (client, _status) = jack::Client::new("rust_jack_simple", jack::ClientOptions::NO_START_SERVER).unwrap(); // Register ports. They will be used in a callback that will be // called when new data is available. - let in_a = client.register_port("rust_in_l", jack::AudioIn).unwrap(); - let in_b = client.register_port("rust_in_r", jack::AudioIn).unwrap(); - let mut out_a = client.register_port("rust_out_l", jack::AudioOut).unwrap(); - let mut out_b = client.register_port("rust_out_r", jack::AudioOut).unwrap(); + let in_a = client + .register_port("rust_in_l", jack::AudioIn::default()) + .unwrap(); + let in_b = client + .register_port("rust_in_r", jack::AudioIn::default()) + .unwrap(); + let mut out_a = client + .register_port("rust_out_l", jack::AudioOut::default()) + .unwrap(); + let mut out_b = client + .register_port("rust_out_r", jack::AudioOut::default()) + .unwrap(); let process_callback = move |_: &jack::Client, ps: &jack::ProcessScope| -> jack::Control { let out_a_p = out_a.as_mut_slice(ps); let out_b_p = out_b.as_mut_slice(ps); diff --git a/examples/sine.rs b/examples/sine.rs index 8cd2e238f..6232a87f7 100644 --- a/examples/sine.rs +++ b/examples/sine.rs @@ -11,7 +11,9 @@ fn main() { jack::Client::new("rust_jack_sine", jack::ClientOptions::NO_START_SERVER).unwrap(); // 2. register port - let mut out_port = client.register_port("sine_out", jack::AudioOut).unwrap(); + let mut out_port = client + .register_port("sine_out", jack::AudioOut::default()) + .unwrap(); // 3. define process callback handler let mut frequency = 220.0; diff --git a/src/client/async_client.rs b/src/client/async_client.rs index ed57aad29..52fdc0287 100644 --- a/src/client/async_client.rs +++ b/src/client/async_client.rs @@ -52,7 +52,7 @@ where /// `notification_handler` and `process_handler` are consumed, but they are returned when /// `Client::deactivate` is called. pub fn new(client: Client, notification_handler: N, process_handler: P) -> Result { - let _m = CREATE_OR_DESTROY_CLIENT_MUTEX.lock().unwrap(); + let _m = CREATE_OR_DESTROY_CLIENT_MUTEX.lock().ok(); unsafe { sleep_on_test(); let mut callback_context = Box::new(CallbackContext { @@ -107,7 +107,7 @@ impl AsyncClient { // Helper function for deactivating. Any function that calls this should // have ownership of self and no longer use it after this call. unsafe fn maybe_deactivate(&mut self) -> Result>, Error> { - let _m = CREATE_OR_DESTROY_CLIENT_MUTEX.lock().unwrap(); + let _m = CREATE_OR_DESTROY_CLIENT_MUTEX.lock().ok(); if self.callback.is_none() { return Err(Error::ClientIsNoLongerAlive); } diff --git a/src/client/client_impl.rs b/src/client/client_impl.rs index e6dfcf672..932cde074 100644 --- a/src/client/client_impl.rs +++ b/src/client/client_impl.rs @@ -1,6 +1,5 @@ use jack_sys as j; use std::fmt::Debug; -use std::panic::catch_unwind; use std::sync::Arc; use std::{ffi, fmt, ptr}; @@ -51,7 +50,7 @@ impl Client { /// Although the client may be successful in opening, there still may be some errors minor /// errors when attempting to opening. To access these, check the returned `ClientStatus`. pub fn new(client_name: &str, options: ClientOptions) -> Result<(Self, ClientStatus), Error> { - let _m = CREATE_OR_DESTROY_CLIENT_MUTEX.lock().unwrap(); + let _m = CREATE_OR_DESTROY_CLIENT_MUTEX.lock().ok(); // All of the jack_sys functions below assume the client library is loaded and will panic if // it is not @@ -60,10 +59,7 @@ impl Client { return Err(Error::LibraryError(err.to_string())); } - unsafe { - jack_sys::jack_set_error_function(Some(silent_handler)); - jack_sys::jack_set_info_function(Some(silent_handler)); - } + crate::logging::maybe_init_logging(); sleep_on_test(); let mut status_bits = 0; let client = unsafe { @@ -75,10 +71,6 @@ impl Client { if client.is_null() { Err(Error::ClientError(status)) } else { - unsafe { - jack_sys::jack_set_error_function(Some(error_handler)); - jack_sys::jack_set_info_function(Some(info_handler)); - } sleep_on_test(); Ok((Client(client, Arc::default(), None), status)) } @@ -552,7 +544,7 @@ impl Client { source_port: &Port, destination_port: &Port, ) -> Result<(), Error> { - let _m = CREATE_OR_DESTROY_CLIENT_MUTEX.lock().unwrap(); + let _m = CREATE_OR_DESTROY_CLIENT_MUTEX.lock().ok(); self.connect_ports_by_name(&source_port.name()?, &destination_port.name()?) } @@ -670,7 +662,7 @@ impl Client { /// Close the client. impl Drop for Client { fn drop(&mut self) { - let _m = CREATE_OR_DESTROY_CLIENT_MUTEX.lock().unwrap(); + let _m = CREATE_OR_DESTROY_CLIENT_MUTEX.lock().ok(); debug_assert!(!self.raw().is_null()); // Rep invariant // Close the client sleep_on_test(); @@ -790,27 +782,3 @@ pub struct CycleTimes { pub next_usecs: Time, pub period_usecs: libc::c_float, } - -unsafe extern "C" fn error_handler(msg: *const libc::c_char) { - let res = catch_unwind(|| match std::ffi::CStr::from_ptr(msg).to_str() { - Ok(msg) => log::error!("{}", msg), - Err(err) => log::error!("failed to log to JACK error: {:?}", err), - }); - if let Err(err) = res { - eprintln!("{err:?}"); - std::mem::forget(err); - } -} - -unsafe extern "C" fn info_handler(msg: *const libc::c_char) { - let res = catch_unwind(|| match std::ffi::CStr::from_ptr(msg).to_str() { - Ok(msg) => log::info!("{}", msg), - Err(err) => log::error!("failed to log to JACK info: {:?}", err), - }); - if let Err(err) = res { - eprintln!("{err:?}"); - std::mem::forget(err); - } -} - -unsafe extern "C" fn silent_handler(_msg: *const libc::c_char) {} diff --git a/src/client/test_callback.rs b/src/client/test_callback.rs index 57e5890fe..28da777b6 100644 --- a/src/client/test_callback.rs +++ b/src/client/test_callback.rs @@ -211,8 +211,14 @@ fn client_cback_reports_xruns() { #[test] fn client_cback_calls_port_registered() { let ac = active_test_client("client_cback_cpr"); - let _pa = ac.as_client().register_port("pa", AudioIn).unwrap(); - let _pb = ac.as_client().register_port("pb", AudioIn).unwrap(); + let _pa = ac + .as_client() + .register_port("pa", AudioIn::default()) + .unwrap(); + let _pb = ac + .as_client() + .register_port("pb", AudioIn::default()) + .unwrap(); let counter = ac.deactivate().unwrap().1; assert_eq!( counter.port_register_history.len(), @@ -228,8 +234,14 @@ fn client_cback_calls_port_registered() { #[test] fn client_cback_calls_port_unregistered() { let ac = active_test_client("client_cback_cpr"); - let pa = ac.as_client().register_port("pa", AudioIn).unwrap(); - let pb = ac.as_client().register_port("pb", AudioIn).unwrap(); + let pa = ac + .as_client() + .register_port("pa", AudioIn::default()) + .unwrap(); + let pb = ac + .as_client() + .register_port("pb", AudioIn::default()) + .unwrap(); ac.as_client().unregister_port(pa).unwrap(); ac.as_client().unregister_port(pb).unwrap(); let counter = ac.deactivate().unwrap().1; diff --git a/src/lib.rs b/src/lib.rs index f7ca0b206..45bb393c9 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -38,6 +38,7 @@ pub use crate::client::{ InternalClientID, NotificationHandler, ProcessHandler, ProcessScope, CLIENT_NAME_SIZE, }; pub use crate::jack_enums::{Control, Error, LatencyType}; +pub use crate::logging::{set_logger, LoggerType}; pub use crate::port::{ AudioIn, AudioOut, MidiIn, MidiIter, MidiOut, MidiWriter, Port, PortFlags, PortSpec, RawMidi, Unowned, PORT_NAME_SIZE, PORT_TYPE_SIZE, @@ -49,36 +50,23 @@ pub use crate::transport::{ TransportStatePosition, }; -/// The underlying system bindings for JACK. Can be useful for using possibly -/// experimental stuff through `jack_sys::library()`. +/// The underlying system bindings for JACK. Can be useful for using possibly experimental stuff +/// through `jack_sys::library()`. pub use jack_sys; //only expose metadata if enabled #[cfg(feature = "metadata")] pub use crate::properties::*; -/// Create and manage client connections to a JACK server. mod client; - -/// Create and manage JACK ring buffers. -mod ringbuffer; - -/// Enum types in jack. mod jack_enums; - mod jack_utils; - -/// Types for safely interacting with port data from JACK. +mod logging; mod port; - -/// Platform independent types. mod primitive_types; - -/// Transport. -mod transport; - -/// Properties mod properties; +mod ringbuffer; +mod transport; static TIME_CLIENT: std::sync::LazyLock = std::sync::LazyLock::new(|| { Client::new("deprecated_get_time", ClientOptions::NO_START_SERVER) diff --git a/src/logging.rs b/src/logging.rs new file mode 100644 index 000000000..fd3c9b43a --- /dev/null +++ b/src/logging.rs @@ -0,0 +1,111 @@ +use std::panic::catch_unwind; + +static INIT_LOGGING: std::sync::Once = std::sync::Once::new(); + +pub(crate) fn maybe_init_logging() { + INIT_LOGGING.call_once_force(|state| { + if state.is_poisoned() { + return; + } + set_logger_impl(LoggerType::default()); + }); +} + +/// Describes how JACK should log info and error messages. +#[derive(Copy, Clone, Debug, PartialEq)] +pub enum LoggerType { + /// Ignore all logging from JACK. + None, + /// Use stdout and stderr to print messages. + Stdio, + /// Use the info! and error! macro from the [log crate](https://crates.io/crates/log). + #[cfg(feature = "log")] + Log, +} + +impl Default for LoggerType { + #[cfg(feature = "log")] + fn default() -> LoggerType { + LoggerType::Log + } + + #[cfg(not(feature = "log"))] + fn default() -> LoggerType { + LoggerType::Stdio + } +} + +/// Set the logger. +pub fn set_logger(logger: LoggerType) { + // Prevents maybe_init_logging from resetting the logger. + if !INIT_LOGGING.is_completed() { + INIT_LOGGING.call_once(|| {}); + } + set_logger_impl(logger); +} + +fn set_logger_impl(logger: LoggerType) { + match logger { + LoggerType::None => unsafe { + jack_sys::jack_set_error_function(Some(silent_handler)); + jack_sys::jack_set_info_function(Some(silent_handler)); + }, + LoggerType::Stdio => unsafe { + jack_sys::jack_set_error_function(Some(stderr_handler)); + jack_sys::jack_set_info_function(Some(stdout_handler)); + }, + #[cfg(feature = "log")] + LoggerType::Log => unsafe { + jack_sys::jack_set_error_function(Some(error_handler)); + jack_sys::jack_set_info_function(Some(info_handler)); + }, + } +} + +#[cfg(feature = "log")] +unsafe extern "C" fn error_handler(msg: *const libc::c_char) { + let res = catch_unwind(|| match std::ffi::CStr::from_ptr(msg).to_str() { + Ok(msg) => log::error!("{}", msg), + Err(err) => log::error!("failed to log to JACK error: {:?}", err), + }); + if let Err(err) = res { + eprintln!("{err:?}"); + std::mem::forget(err); + } +} + +#[cfg(feature = "log")] +unsafe extern "C" fn info_handler(msg: *const libc::c_char) { + let res = catch_unwind(|| match std::ffi::CStr::from_ptr(msg).to_str() { + Ok(msg) => log::info!("{}", msg), + Err(err) => log::error!("failed to log to JACK info: {:?}", err), + }); + if let Err(err) = res { + eprintln!("{err:?}"); + std::mem::forget(err); + } +} + +unsafe extern "C" fn stderr_handler(msg: *const libc::c_char) { + let res = catch_unwind(|| match std::ffi::CStr::from_ptr(msg).to_str() { + Ok(msg) => eprintln!("{}", msg), + Err(err) => eprintln!("failed to log to JACK error: {:?}", err), + }); + if let Err(err) = res { + eprintln!("{err:?}"); + std::mem::forget(err); + } +} + +unsafe extern "C" fn stdout_handler(msg: *const libc::c_char) { + let res = catch_unwind(|| match std::ffi::CStr::from_ptr(msg).to_str() { + Ok(msg) => println!("{}", msg), + Err(err) => println!("failed to log to JACK info: {:?}", err), + }); + if let Err(err) = res { + eprintln!("{err:?}"); + std::mem::forget(err); + } +} + +unsafe extern "C" fn silent_handler(_msg: *const libc::c_char) {} diff --git a/src/port/audio.rs b/src/port/audio.rs index ab4448140..61bceeb97 100644 --- a/src/port/audio.rs +++ b/src/port/audio.rs @@ -18,7 +18,9 @@ use crate::{Port, PortFlags, PortSpec, ProcessScope}; /// let audio_in_port = client.register_port("in", spec).unwrap(); /// ``` #[derive(Copy, Clone, Debug, Default)] -pub struct AudioIn; +pub struct AudioIn { + _internal: (), +} /// `AudioOut` implements the `PortSpec` trait, which defines an /// endpoint for JACK. In this case, it is a mutable 32 bit floating @@ -35,7 +37,9 @@ pub struct AudioIn; /// let audio_out_port = client.register_port("out", spec).unwrap(); /// ``` #[derive(Copy, Clone, Debug, Default)] -pub struct AudioOut; +pub struct AudioOut { + _internal: (), +} unsafe impl PortSpec for AudioOut { fn jack_port_type(&self) -> &'static str { @@ -105,10 +109,10 @@ mod test { #[test] fn port_audio_can_read_write() { let c = open_test_client("port_audio_crw"); - let in_a = c.register_port("ia", AudioIn).unwrap(); - let in_b = c.register_port("ib", AudioIn).unwrap(); - let mut out_a = c.register_port("oa", AudioOut).unwrap(); - let mut out_b = c.register_port("ob", AudioOut).unwrap(); + let in_a = c.register_port("ia", AudioIn::default()).unwrap(); + let in_b = c.register_port("ib", AudioIn::default()).unwrap(); + let mut out_a = c.register_port("oa", AudioOut::default()).unwrap(); + let mut out_b = c.register_port("ob", AudioOut::default()).unwrap(); let (success_sender, success_receiver) = std::sync::mpsc::sync_channel(1); let process_callback = move |_: &Client, ps: &ProcessScope| -> Control { let exp_a = 0.312_443; diff --git a/src/port/test_client.rs b/src/port/test_client.rs index 50ccfab9e..9d63bd8c4 100644 --- a/src/port/test_client.rs +++ b/src/port/test_client.rs @@ -15,16 +15,16 @@ fn open_test_client(name: &str) -> Client { #[test] fn client_port_can_register_port() { let c = open_test_client("cp_can_register_port"); - c.register_port("cpcrp_a", AudioIn).unwrap(); + c.register_port("cpcrp_a", AudioIn::default()).unwrap(); } #[test] fn client_port_register_port_enforces_unique_names() { let pname = "cprpeun_a"; let c = open_test_client("cp_can_register_port"); - c.register_port(pname, AudioIn).unwrap(); + c.register_port(pname, AudioIn::default()).unwrap(); assert_eq!( - c.register_port(pname, AudioIn).err(), + c.register_port(pname, AudioIn::default()).err(), Some(Error::PortRegistrationError(pname.to_string())) ); } @@ -37,7 +37,7 @@ fn client_port_register_port_enforces_name_length() { .collect::>() .join("_"); assert_eq!( - c.register_port(&pname, AudioIn).err(), + c.register_port(&pname, AudioIn::default()).err(), Some(Error::PortRegistrationError(pname.to_string())) ); } @@ -45,7 +45,7 @@ fn client_port_register_port_enforces_name_length() { #[test] fn client_port_can_request_monitor_by_name() { let c = open_test_client("cp_can_request_monitor_by_name"); - let p = c.register_port("cpcrmbn_a", AudioIn).unwrap(); + let p = c.register_port("cpcrmbn_a", AudioIn::default()).unwrap(); c.request_monitor_by_name(&p.name().unwrap(), true).unwrap(); c.request_monitor_by_name(&p.name().unwrap(), false) .unwrap(); @@ -54,7 +54,7 @@ fn client_port_can_request_monitor_by_name() { #[test] fn client_port_can_get_port_by_name() { let c = open_test_client("cp_can_get_port_by_name"); - let p = c.register_port("named_port", AudioIn).unwrap(); + let p = c.register_port("named_port", AudioIn::default()).unwrap(); let _p = c.port_by_name(&p.name().unwrap()).unwrap(); } @@ -85,7 +85,10 @@ fn client_port_can_get_port_by_id() { let ac = c.activate_async(h, ()).unwrap(); // Register port - let _pa = ac.as_client().register_port(port_name, AudioIn).unwrap(); + let _pa = ac + .as_client() + .register_port(port_name, AudioIn::default()) + .unwrap(); // Get by id let c = ac.deactivate().unwrap().0; @@ -108,7 +111,7 @@ fn client_port_can_get_port_by_id() { #[test] fn client_port_fails_to_nonexistant_port() { let c = open_test_client("cp_can_request_monitor_by_name"); - let p = c.register_port("cpcrmbn_a", AudioIn).unwrap(); + let p = c.register_port("cpcrmbn_a", AudioIn::default()).unwrap(); let _p = c.port_by_name(&p.name().unwrap()).unwrap(); } @@ -116,8 +119,8 @@ fn client_port_fails_to_nonexistant_port() { fn client_port_recognizes_my_ports() { let ca = open_test_client("cp_cprmp_ca"); let cb = open_test_client("cp_cprmp_cb"); - let first = ca.register_port("cpcprmp_pa", AudioIn).unwrap(); - let second = cb.register_port("cpcprmp_pb", AudioIn).unwrap(); + let first = ca.register_port("cpcprmp_pa", AudioIn::default()).unwrap(); + let second = cb.register_port("cpcprmp_pb", AudioIn::default()).unwrap(); let first_alt = ca.port_by_name(&first.name().unwrap()).unwrap(); let second_alt = ca.port_by_name(&second.name().unwrap()).unwrap(); assert!(ca.is_mine(&first)); @@ -131,8 +134,8 @@ fn client_port_can_connect_ports() { let client = open_test_client("client_port_ccp"); // initialize ports - let in_p = client.register_port("inp", AudioIn).unwrap(); - let out_p = client.register_port("outp", AudioOut).unwrap(); + let in_p = client.register_port("inp", AudioIn::default()).unwrap(); + let out_p = client.register_port("outp", AudioOut::default()).unwrap(); // start client let client = client.activate_async((), ()).unwrap(); @@ -146,8 +149,8 @@ fn client_port_can_connect_ports_by_name() { let client = open_test_client("client_port_ccpbn"); // initialize ports - let _in_p = client.register_port("inp", AudioIn).unwrap(); - let _out_p = client.register_port("outp", AudioOut).unwrap(); + let _in_p = client.register_port("inp", AudioIn::default()).unwrap(); + let _out_p = client.register_port("outp", AudioOut::default()).unwrap(); // start client let client = client.activate_async((), ()).unwrap(); @@ -165,8 +168,8 @@ fn client_port_can_connect_unowned_ports() { let connector = open_test_client("client_port_ccup_conn"); // initialize ports - let _in_p = client.register_port("inp", AudioIn).unwrap(); - let _out_p = client.register_port("outp", AudioOut).unwrap(); + let _in_p = client.register_port("inp", AudioIn::default()).unwrap(); + let _out_p = client.register_port("outp", AudioOut::default()).unwrap(); // start client let _client = client.activate_async((), ()).unwrap(); @@ -183,9 +186,13 @@ fn client_port_cant_connect_inactive_client() { let other = open_test_client("client_port_ccic_other"); // initialize ports - let in_p = other.register_port("inp", AudioIn).unwrap().name().unwrap(); + let in_p = other + .register_port("inp", AudioIn::default()) + .unwrap() + .name() + .unwrap(); let out_p = other - .register_port("outp", AudioOut) + .register_port("outp", AudioOut::default()) .unwrap() .name() .unwrap(); @@ -207,8 +214,8 @@ fn client_port_recognizes_already_connected_ports() { let client = open_test_client("client_port_racp"); // initialize ports - let in_p = client.register_port("conna", AudioIn).unwrap(); - let out_p = client.register_port("connb", AudioOut).unwrap(); + let in_p = client.register_port("conna", AudioIn::default()).unwrap(); + let out_p = client.register_port("connb", AudioOut::default()).unwrap(); // start client let client = client.activate_async((), ()).unwrap(); @@ -245,8 +252,8 @@ fn client_port_can_disconnect_port_from_all() { let client = open_test_client("client_port_cdpfa"); // initialize ports - let in_p = client.register_port("conna", AudioIn).unwrap(); - let out_p = client.register_port("connb", AudioOut).unwrap(); + let in_p = client.register_port("conna", AudioIn::default()).unwrap(); + let out_p = client.register_port("connb", AudioOut::default()).unwrap(); // start client let client = client.activate_async((), ()).unwrap(); @@ -261,8 +268,8 @@ fn client_port_can_disconnect_ports() { let client = open_test_client("client_port_cdp"); // initialize ports - let in_p = client.register_port("conna", AudioIn).unwrap(); - let out_p = client.register_port("connb", AudioOut).unwrap(); + let in_p = client.register_port("conna", AudioIn::default()).unwrap(); + let out_p = client.register_port("connb", AudioOut::default()).unwrap(); // start client let client = client.activate_async((), ()).unwrap(); @@ -277,8 +284,8 @@ fn client_port_can_disconnect_ports_by_name() { let client = open_test_client("client_port_cdpbn"); // initialize ports - let in_p = client.register_port("conna", AudioIn).unwrap(); - let out_p = client.register_port("connb", AudioOut).unwrap(); + let in_p = client.register_port("conna", AudioIn::default()).unwrap(); + let out_p = client.register_port("connb", AudioOut::default()).unwrap(); // start client let client = client.activate_async((), ()).unwrap(); @@ -300,8 +307,8 @@ fn client_port_can_disconnect_unowned_ports() { let disconnector = open_test_client("client_port_cdup_disc"); // initialize ports - let in_p = client.register_port("conna", AudioIn).unwrap(); - let out_p = client.register_port("connb", AudioOut).unwrap(); + let in_p = client.register_port("conna", AudioIn::default()).unwrap(); + let out_p = client.register_port("connb", AudioOut::default()).unwrap(); // start client let client = client.activate_async((), ()).unwrap(); @@ -322,8 +329,8 @@ fn client_port_can_get_existing_ports() { let port_getter = open_test_client("client_port_cgep_getter"); // initialize ports - let in_p = client.register_port("conna", AudioIn).unwrap(); - let out_p = client.register_port("connb", AudioOut).unwrap(); + let in_p = client.register_port("conna", AudioIn::default()).unwrap(); + let out_p = client.register_port("connb", AudioOut::default()).unwrap(); // retrieve let known_ports = [ diff --git a/src/port/test_port.rs b/src/port/test_port.rs index 6b80602c8..a6b253ea2 100644 --- a/src/port/test_port.rs +++ b/src/port/test_port.rs @@ -13,7 +13,7 @@ fn open_test_client(name: &str) -> Client { fn open_client_with_port(client: &str, port: &str) -> (Client, Port) { let c = open_test_client(client); - let p = c.register_port(port, AudioIn).unwrap(); + let p = c.register_port(port, AudioIn::default()).unwrap(); (c, p) } @@ -52,10 +52,18 @@ fn port_can_rename() { #[test] fn port_connected_count() { let c = open_test_client("port_connected_count"); - let pa = c.register_port("port_connected_count_a", AudioIn).unwrap(); - let pb = c.register_port("port_connected_count_b", AudioOut).unwrap(); - let pc = c.register_port("port_connected_count_c", AudioOut).unwrap(); - let pd = c.register_port("port_connected_count_d", AudioOut).unwrap(); + let pa = c + .register_port("port_connected_count_a", AudioIn::default()) + .unwrap(); + let pb = c + .register_port("port_connected_count_b", AudioOut::default()) + .unwrap(); + let pc = c + .register_port("port_connected_count_c", AudioOut::default()) + .unwrap(); + let pd = c + .register_port("port_connected_count_d", AudioOut::default()) + .unwrap(); let c = c.activate_async((), ()).unwrap(); c.as_client().connect_ports(&pb, &pa).unwrap(); c.as_client().connect_ports(&pc, &pa).unwrap(); @@ -68,10 +76,10 @@ fn port_connected_count() { #[test] fn port_knows_connections() { let c = open_test_client("port_knows_connections"); - let pa = c.register_port("pa", AudioIn).unwrap(); - let pb = c.register_port("pb", AudioOut).unwrap(); - let pc = c.register_port("pc", AudioOut).unwrap(); - let pd = c.register_port("pd", AudioOut).unwrap(); + let pa = c.register_port("pa", AudioIn::default()).unwrap(); + let pb = c.register_port("pb", AudioOut::default()).unwrap(); + let pc = c.register_port("pc", AudioOut::default()).unwrap(); + let pd = c.register_port("pd", AudioOut::default()).unwrap(); let c = c.activate_async((), ()).unwrap(); c.as_client().connect_ports(&pb, &pa).unwrap(); c.as_client().connect_ports(&pc, &pa).unwrap();