libddwaf/
handle.rs

1use std::ffi::CStr;
2
3use crate::Context;
4
5/// A fully configured WAF instance.
6///
7/// This is obtained by [`Builder::build`][crate::Builder::build] and provides facility to create new [`Context`]
8/// that use the underlying instance's configuration.
9#[repr(transparent)]
10pub struct Handle {
11    pub(crate) raw: libddwaf_sys::ddwaf_handle,
12}
13impl Handle {
14    /// Creates a new [`Context`] from this instance.
15    #[must_use]
16    pub fn new_context(&self) -> Context {
17        Context {
18            raw: unsafe { libddwaf_sys::ddwaf_context_init(self.raw) },
19            keepalive: Vec::new(),
20        }
21    }
22
23    /// Returns the list of actions that may be produced by this instance's ruleset.
24    pub fn known_actions(&self) -> Vec<&CStr> {
25        self.call_cstr_array_fn(libddwaf_sys::ddwaf_known_actions)
26    }
27
28    /// Returns the list of addresses that are used by this instance's ruleset.
29    ///
30    /// Sending data for addresses not in this list to [`Context::run`] should be avoided as this
31    /// data will never result in any side-effects.
32    pub fn known_addresses(&self) -> Vec<&CStr> {
33        self.call_cstr_array_fn(libddwaf_sys::ddwaf_known_addresses)
34    }
35
36    fn call_cstr_array_fn(
37        &self,
38        f: unsafe extern "C" fn(
39            libddwaf_sys::ddwaf_handle,
40            *mut u32,
41        ) -> *const *const std::os::raw::c_char,
42    ) -> Vec<&CStr> {
43        let mut size = std::mem::MaybeUninit::<u32>::uninit();
44        let ptr = unsafe { f(self.raw, size.as_mut_ptr()) };
45        if ptr.is_null() {
46            return vec![];
47        }
48        let size = unsafe { size.assume_init() as usize };
49        let arr = unsafe { std::slice::from_raw_parts(ptr, size) };
50        arr.iter().map(|&x| unsafe { CStr::from_ptr(x) }).collect()
51    }
52}
53impl Drop for Handle {
54    fn drop(&mut self) {
55        unsafe { libddwaf_sys::ddwaf_destroy(self.raw) }
56    }
57}
58// SAFETY: ddwaf instances are effectively immutable
59unsafe impl Send for Handle {}
60// SAFETY: ddwaf instances are effectively immutable
61unsafe impl Sync for Handle {}