diff options
| author | Linus Färnstrand <linus@mullvad.net> | 2017-03-06 19:41:33 +0100 |
|---|---|---|
| committer | Linus Färnstrand <linus@mullvad.net> | 2017-03-07 08:42:02 +0100 |
| commit | ae3458fdd2ee092924ce2f275e622f6a66fab903 (patch) | |
| tree | a6f5a196c0c0b7d3b5b9080ce7d80e9bfb4b2210 | |
| parent | f085642d25c2f91095ce01d324a59b5cee23e8b0 (diff) | |
| download | mullvadvpn-ae3458fdd2ee092924ce2f275e622f6a66fab903.tar.xz mullvadvpn-ae3458fdd2ee092924ce2f275e622f6a66fab903.zip | |
Extract OpenVPN FFI stuff to separate crate
| -rw-r--r-- | Cargo.lock | 10 | ||||
| -rw-r--r-- | Cargo.toml | 2 | ||||
| -rw-r--r-- | openvpn_ffi/Cargo.toml | 11 | ||||
| -rw-r--r-- | openvpn_ffi/src/lib.rs (renamed from talpid_openvpn_plugin/src/ffi/consts.rs) | 65 | ||||
| -rw-r--r-- | openvpn_ffi/src/parse.rs (renamed from talpid_openvpn_plugin/src/ffi/parse.rs) | 0 | ||||
| -rw-r--r-- | openvpn_ffi/src/structs.rs (renamed from talpid_openvpn_plugin/src/ffi/structs.rs) | 0 | ||||
| -rw-r--r-- | talpid_openvpn_plugin/Cargo.toml | 4 | ||||
| -rw-r--r-- | talpid_openvpn_plugin/src/ffi/mod.rs | 55 | ||||
| -rw-r--r-- | talpid_openvpn_plugin/src/lib.rs | 48 | ||||
| -rw-r--r-- | talpid_openvpn_plugin/src/processing.rs | 5 |
10 files changed, 104 insertions, 96 deletions
diff --git a/Cargo.lock b/Cargo.lock index ab64cc5d51..d6b275ace6 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -2,10 +2,10 @@ name = "talpid_openvpn_plugin" version = "0.1.0" dependencies = [ - "assert_matches 1.0.1 (registry+https://github.com/rust-lang/crates.io-index)", "env_logger 0.4.1 (registry+https://github.com/rust-lang/crates.io-index)", "error-chain 0.8.1 (registry+https://github.com/rust-lang/crates.io-index)", "log 0.3.6 (registry+https://github.com/rust-lang/crates.io-index)", + "openvpn_ffi 0.1.0", "talpid_ipc 0.1.0", ] @@ -172,6 +172,14 @@ version = "0.1.37" source = "registry+https://github.com/rust-lang/crates.io-index" [[package]] +name = "openvpn_ffi" +version = "0.1.0" +dependencies = [ + "assert_matches 1.0.1 (registry+https://github.com/rust-lang/crates.io-index)", + "error-chain 0.8.1 (registry+https://github.com/rust-lang/crates.io-index)", +] + +[[package]] name = "pkg-config" version = "0.3.9" source = "registry+https://github.com/rust-lang/crates.io-index" diff --git a/Cargo.toml b/Cargo.toml index 7ac25c9748..c47e370320 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -18,4 +18,4 @@ zmq = "0.8" assert_matches = "1.0" [workspace] -members = ["talpid_openvpn_plugin", "talpid_cli", "talpid_ipc"] +members = ["talpid_openvpn_plugin", "openvpn_ffi", "talpid_cli", "talpid_ipc"] diff --git a/openvpn_ffi/Cargo.toml b/openvpn_ffi/Cargo.toml new file mode 100644 index 0000000000..0ad09ce919 --- /dev/null +++ b/openvpn_ffi/Cargo.toml @@ -0,0 +1,11 @@ +[package] +name = "openvpn_ffi" +version = "0.1.0" +authors = ["Linus Färnstrand <linus@mullvad.net>", "Erik Larkö <erik@mullvad.net>"] +description = "Constants, enums and structs for interfacing with OpenVPN" + +[dependencies] +error-chain = "0.8" + +[dev-dependencies] +assert_matches = "1.0" diff --git a/talpid_openvpn_plugin/src/ffi/consts.rs b/openvpn_ffi/src/lib.rs index cf5490afbc..6deed54e37 100644 --- a/talpid_openvpn_plugin/src/ffi/consts.rs +++ b/openvpn_ffi/src/lib.rs @@ -1,8 +1,20 @@ -/// Constants for OpenVPN. Taken from include/openvpn-plugin.h in the OpenVPN repository: -/// https://github.com/OpenVPN/openvpn/blob/master/include/openvpn-plugin.h.in +//! Constants for OpenVPN. Taken from include/openvpn-plugin.h in the OpenVPN repository: +//! https://github.com/OpenVPN/openvpn/blob/master/include/openvpn-plugin.h.in + +#[macro_use] +extern crate error_chain; + +#[cfg(test)] +#[macro_use] +extern crate assert_matches; use std::os::raw::c_int; +mod structs; +pub use structs::*; + +pub mod parse; + error_chain!{ errors { InvalidEnumVariant(i: c_int) { @@ -12,6 +24,14 @@ error_chain!{ } } + +// Return values. Returned from the plugin to OpenVPN to indicate success or failure. Can also +// Accept (success) or decline (error) an operation, such as incoming client connection attempt. +pub const OPENVPN_PLUGIN_FUNC_SUCCESS: c_int = 0; +pub const OPENVPN_PLUGIN_FUNC_ERROR: c_int = 1; +pub const OPENVPN_PLUGIN_FUNC_DEFERRED: c_int = 2; + + /// Enum whose variants correspond to the `OPENVPN_PLUGIN_*` event constants. #[derive(Debug, Copy, Clone, Eq, PartialEq, Hash)] pub enum OpenVpnPluginEvent { @@ -42,14 +62,15 @@ impl OpenVpnPluginEvent { } } - -// Return values. Returned from the plugin to OpenVPN to indicate success or failure. Can also -// Accept (success) or decline (error) an operation, such as incoming client connection attempt. -pub const OPENVPN_PLUGIN_FUNC_SUCCESS: c_int = 0; -pub const OPENVPN_PLUGIN_FUNC_ERROR: c_int = 1; -#[allow(dead_code)] -pub const OPENVPN_PLUGIN_FUNC_DEFERRED: c_int = 2; - +/// Translates a collection of `OpenVpnPluginEvent` instances into a bitmask in the format OpenVPN +/// expects it. +pub fn events_to_bitmask(events: &[OpenVpnPluginEvent]) -> c_int { + let mut bitmask: c_int = 0; + for event in events { + bitmask |= 1 << (*event as i32); + } + bitmask +} #[cfg(test)] @@ -94,4 +115,28 @@ mod tests { let result = format!("{:?}", OpenVpnPluginEvent::Up); assert_eq!("Up", result); } + + #[test] + fn events_to_bitmask_no_events() { + let result = events_to_bitmask(&[]); + assert_eq!(0, result); + } + + #[test] + fn events_to_bitmask_one_event() { + let result = events_to_bitmask(&[OpenVpnPluginEvent::Up]); + assert_eq!(0b1, result); + } + + #[test] + fn events_to_bitmask_another_event() { + let result = events_to_bitmask(&[OpenVpnPluginEvent::RouteUp]); + assert_eq!(0b100, result); + } + + #[test] + fn events_to_bitmask_many_events() { + let result = events_to_bitmask(&[OpenVpnPluginEvent::RouteUp, OpenVpnPluginEvent::N]); + assert_eq!((1 << 13) + (1 << 2), result); + } } diff --git a/talpid_openvpn_plugin/src/ffi/parse.rs b/openvpn_ffi/src/parse.rs index 096e3ada55..096e3ada55 100644 --- a/talpid_openvpn_plugin/src/ffi/parse.rs +++ b/openvpn_ffi/src/parse.rs diff --git a/talpid_openvpn_plugin/src/ffi/structs.rs b/openvpn_ffi/src/structs.rs index b80f7ae2a2..b80f7ae2a2 100644 --- a/talpid_openvpn_plugin/src/ffi/structs.rs +++ b/openvpn_ffi/src/structs.rs diff --git a/talpid_openvpn_plugin/Cargo.toml b/talpid_openvpn_plugin/Cargo.toml index ca870cb1cb..b98794dce1 100644 --- a/talpid_openvpn_plugin/Cargo.toml +++ b/talpid_openvpn_plugin/Cargo.toml @@ -15,5 +15,5 @@ env_logger = "0.4" [dependencies.talpid_ipc] path = "../talpid_ipc" -[dev-dependencies] -assert_matches = "1.0" +[dependencies.openvpn_ffi] +path = "../openvpn_ffi" diff --git a/talpid_openvpn_plugin/src/ffi/mod.rs b/talpid_openvpn_plugin/src/ffi/mod.rs deleted file mode 100644 index fe046cde67..0000000000 --- a/talpid_openvpn_plugin/src/ffi/mod.rs +++ /dev/null @@ -1,55 +0,0 @@ -// FFI definitions for OpenVPN. See include/openvpn-plugin.h in the OpenVPN repository for -// the original declarations of these structs and functions along with documentation for them: -// https://github.com/OpenVPN/openvpn/blob/master/include/openvpn-plugin.h.in - -use std::os::raw::c_int; - -mod consts; -pub use self::consts::*; - -mod structs; -pub use self::structs::*; - -pub mod parse; - - - -/// Translates a collection of `OpenVpnPluginEvent` instances into a bitmask in the format OpenVPN -/// expects it. -pub fn events_to_bitmask(events: &[OpenVpnPluginEvent]) -> c_int { - let mut bitmask: c_int = 0; - for event in events { - bitmask |= 1 << (*event as i32); - } - bitmask -} - - -#[cfg(test)] -mod tests { - use super::*; - - #[test] - fn events_to_bitmask_no_events() { - let result = events_to_bitmask(&[]); - assert_eq!(0, result); - } - - #[test] - fn events_to_bitmask_one_event() { - let result = events_to_bitmask(&[OpenVpnPluginEvent::Up]); - assert_eq!(0b1, result); - } - - #[test] - fn events_to_bitmask_another_event() { - let result = events_to_bitmask(&[OpenVpnPluginEvent::RouteUp]); - assert_eq!(0b100, result); - } - - #[test] - fn events_to_bitmask_many_events() { - let result = events_to_bitmask(&[OpenVpnPluginEvent::RouteUp, OpenVpnPluginEvent::N]); - assert_eq!((1 << 13) + (1 << 2), result); - } -} diff --git a/talpid_openvpn_plugin/src/lib.rs b/talpid_openvpn_plugin/src/lib.rs index 58343de791..1b6b1fec2b 100644 --- a/talpid_openvpn_plugin/src/lib.rs +++ b/talpid_openvpn_plugin/src/lib.rs @@ -5,18 +5,13 @@ extern crate error_chain; extern crate log; extern crate env_logger; -#[cfg(test)] -#[macro_use] -extern crate assert_matches; - +extern crate openvpn_ffi; extern crate talpid_ipc; use std::os::raw::{c_int, c_void}; -mod ffi; mod processing; -use ffi::OpenVpnPluginEvent; use processing::EventProcessor; @@ -43,8 +38,8 @@ error_chain!{ /// All the OpenVPN events this plugin will register for listening to. Edit this variable to change /// events. -pub static INTERESTING_EVENTS: &'static [OpenVpnPluginEvent] = &[OpenVpnPluginEvent::Up, - OpenVpnPluginEvent::RoutePredown]; +pub static INTERESTING_EVENTS: &'static [openvpn_ffi::OpenVpnPluginEvent] = + &[openvpn_ffi::OpenVpnPluginEvent::Up, openvpn_ffi::OpenVpnPluginEvent::RoutePredown]; /// Called by OpenVPN when the plugin is first loaded. @@ -53,29 +48,29 @@ pub static INTERESTING_EVENTS: &'static [OpenVpnPluginEvent] = &[OpenVpnPluginEv /// plugin. #[no_mangle] pub extern "C" fn openvpn_plugin_open_v3(_version: c_int, - args: *const ffi::openvpn_plugin_args_open_in, - retptr: *mut ffi::openvpn_plugin_args_open_return) + args: *const openvpn_ffi::openvpn_plugin_args_open_in, + retptr: *mut openvpn_ffi::openvpn_plugin_args_open_return) -> c_int { if init_logger().is_err() { - return ffi::OPENVPN_PLUGIN_FUNC_ERROR; + return openvpn_ffi::OPENVPN_PLUGIN_FUNC_ERROR; } match openvpn_plugin_open_v3_internal(args, retptr) { - Ok(_) => ffi::OPENVPN_PLUGIN_FUNC_SUCCESS, + Ok(_) => openvpn_ffi::OPENVPN_PLUGIN_FUNC_SUCCESS, Err(e) => { log_error("Unable to initialize plugin", &e); - ffi::OPENVPN_PLUGIN_FUNC_ERROR + openvpn_ffi::OPENVPN_PLUGIN_FUNC_ERROR } } } -fn openvpn_plugin_open_v3_internal(args: *const ffi::openvpn_plugin_args_open_in, - retptr: *mut ffi::openvpn_plugin_args_open_return) +fn openvpn_plugin_open_v3_internal(args: *const openvpn_ffi::openvpn_plugin_args_open_in, + retptr: *mut openvpn_ffi::openvpn_plugin_args_open_return) -> Result<()> { debug!("Initializing plugin"); let core_server_id = parse_args(args)?; let processor = EventProcessor::new(core_server_id).chain_err(|| ErrorKind::InitHandleFailed)?; unsafe { - (*retptr).type_mask = ffi::events_to_bitmask(INTERESTING_EVENTS); + (*retptr).type_mask = openvpn_ffi::events_to_bitmask(INTERESTING_EVENTS); // Converting the handle into a raw pointer will make it escape Rust deallocation. See // `openvpn_plugin_close_v1` for deallocation. (*retptr).handle = Box::into_raw(Box::new(processor)) as *const c_void; @@ -83,8 +78,9 @@ fn openvpn_plugin_open_v3_internal(args: *const ffi::openvpn_plugin_args_open_in Ok(()) } -fn parse_args(args: *const ffi::openvpn_plugin_args_open_in) -> Result<talpid_ipc::IpcServerId> { - let mut args_iter = unsafe { ffi::parse::string_array((*args).argv) } +fn parse_args(args: *const openvpn_ffi::openvpn_plugin_args_open_in) + -> Result<talpid_ipc::IpcServerId> { + let mut args_iter = unsafe { openvpn_ffi::parse::string_array((*args).argv) } .chain_err(|| ErrorKind::ParseArgsFailed)? .into_iter(); let _plugin_path = args_iter.next(); @@ -109,23 +105,25 @@ pub extern "C" fn openvpn_plugin_close_v1(handle: *const c_void) { /// `openvpn_plugin_open_v3` #[no_mangle] pub extern "C" fn openvpn_plugin_func_v3(_version: c_int, - args: *const ffi::openvpn_plugin_args_func_in, - _retptr: *const ffi::openvpn_plugin_args_func_return) + args: *const openvpn_ffi::openvpn_plugin_args_func_in, + _retptr: *const openvpn_ffi::openvpn_plugin_args_func_return) -> c_int { match openvpn_plugin_func_v3_internal(args) { - Ok(_) => ffi::OPENVPN_PLUGIN_FUNC_SUCCESS, + Ok(_) => openvpn_ffi::OPENVPN_PLUGIN_FUNC_SUCCESS, Err(e) => { log_error("Error while processing event", &e); - ffi::OPENVPN_PLUGIN_FUNC_ERROR + openvpn_ffi::OPENVPN_PLUGIN_FUNC_ERROR } } } -fn openvpn_plugin_func_v3_internal(args: *const ffi::openvpn_plugin_args_func_in) -> Result<()> { +fn openvpn_plugin_func_v3_internal(args: *const openvpn_ffi::openvpn_plugin_args_func_in) + -> Result<()> { let event_type = unsafe { (*args).event_type }; - let event = OpenVpnPluginEvent::from_int(event_type).chain_err(|| ErrorKind::InvalidEventType)?; + let event = openvpn_ffi::OpenVpnPluginEvent::from_int(event_type).chain_err(|| ErrorKind::InvalidEventType)?; debug!("Received event: {:?}", event); - let env = unsafe { ffi::parse::env((*args).envp) }.chain_err(|| ErrorKind::ParseEnvFailed)?; + let env = + unsafe { openvpn_ffi::parse::env((*args).envp) }.chain_err(|| ErrorKind::ParseEnvFailed)?; let mut handle = unsafe { Box::from_raw((*args).handle as *mut EventProcessor) }; handle.process_event(event, env).chain_err(|| ErrorKind::EventProcessingFailed)?; diff --git a/talpid_openvpn_plugin/src/processing.rs b/talpid_openvpn_plugin/src/processing.rs index 586d0574ec..68bab3b99c 100644 --- a/talpid_openvpn_plugin/src/processing.rs +++ b/talpid_openvpn_plugin/src/processing.rs @@ -1,9 +1,10 @@ -use ffi::OpenVpnPluginEvent; +use openvpn_ffi; use std::collections::HashMap; use talpid_ipc::{IpcClient, IpcServerId}; + error_chain! { errors { IpcSendingError { @@ -26,7 +27,7 @@ impl EventProcessor { } pub fn process_event(&mut self, - event: OpenVpnPluginEvent, + event: openvpn_ffi::OpenVpnPluginEvent, env: HashMap<String, String>) -> Result<()> { trace!("Processing \"{:?}\" event", event); |
