use super::{ffi, gpconf::OpenconnectArgs, vpnc_script::find_default_vpnc_script}; use std::ffi::{c_char, c_void, CString}; #[derive(Debug)] pub(crate) struct VpnOptions { server: CString, cookie: CString, user_agent: CString, script: CString, certificate: Option, servercert: Option, } impl VpnOptions { pub fn builder() -> VpnOptionsBuilder { VpnOptionsBuilder::default() } pub fn as_oc_options(&self, user_data: *mut c_void) -> ffi::Options { ffi::Options { server: self.server.as_ptr(), cookie: self.cookie.as_ptr(), user_agent: self.user_agent.as_ptr(), user_data, script: self.script.as_ptr(), certificate: Self::option_as_ptr(&self.certificate), servercert: Self::option_as_ptr(&self.servercert), } } fn option_as_ptr(value: &Option) -> *const c_char { match value { Some(value) => value.as_ptr(), None => std::ptr::null(), } } } #[derive(Debug, Default)] pub(crate) struct VpnOptionsBuilder { server: String, cookie: String, user_agent: String, openconnect_args: OpenconnectArgs, } impl VpnOptionsBuilder { pub fn server(&mut self, server: &str) -> &mut Self { self.server = server.to_string(); self } pub fn cookie(&mut self, cookie: &str) -> &mut Self { self.cookie = cookie.to_string(); self } pub fn user_agent(&mut self, user_agent: &str) -> &mut Self { self.user_agent = user_agent.to_string(); self } pub fn with_openconnect_args(&mut self, openconnect_args: OpenconnectArgs) -> &mut Self { self.openconnect_args = openconnect_args; self } fn to_cstr(value: &str) -> CString { CString::new(value.to_string()).expect("Failed to convert to CString") } pub fn build(&self) -> VpnOptions { let openconnect_args = &self.openconnect_args; let script = openconnect_args .script() .or_else(|| find_default_vpnc_script().map(|s| s.to_string())) .map(|s| Self::to_cstr(&s)) .unwrap_or_default(); let certificate = openconnect_args.certificate().map(|s| Self::to_cstr(&s)); let servercert = openconnect_args.servercert().map(|s| Self::to_cstr(&s)); VpnOptions { server: Self::to_cstr(&self.server), cookie: Self::to_cstr(&self.cookie), user_agent: Self::to_cstr(&self.user_agent), script, certificate, servercert, } } }