Skip to main content

libgvproxy_sys/
lib.rs

1//! Low-level FFI bindings to libgvproxy
2//!
3//! This crate provides raw, unsafe bindings to the gvproxy-bridge C library.
4//! For a safe, idiomatic Rust API, use the higher-level wrapper in the boxlite crate.
5
6use std::os::raw::{c_char, c_int, c_longlong, c_void};
7
8/// Logging callback function type
9///
10/// Called by Go's slog handler to forward log messages to Rust.
11///
12/// # Arguments
13/// * `level` - Log level (0=trace, 1=debug, 2=info, 3=warn, 4=error)
14/// * `message` - Log message (null-terminated C string)
15pub type LogCallbackFn = extern "C" fn(level: c_int, message: *const c_char);
16
17extern "C" {
18    /// Create a new gvproxy instance with port mappings
19    ///
20    /// # Arguments
21    /// * `portMappingsJSON` - JSON string describing port mappings
22    ///
23    /// # Returns
24    /// Instance ID (handle) or -1 on error
25    pub fn gvproxy_create(portMappingsJSON: *const c_char) -> c_longlong;
26
27    /// Free a string allocated by libgvproxy
28    ///
29    /// # Arguments
30    /// * `str` - Pointer to string returned by gvproxy functions
31    pub fn gvproxy_free_string(str: *mut c_char);
32
33    /// Destroy a gvproxy instance and free resources
34    ///
35    /// # Arguments
36    /// * `id` - Instance ID to destroy
37    ///
38    /// # Returns
39    /// 0 on success, non-zero on error
40    pub fn gvproxy_destroy(id: c_longlong) -> c_int;
41
42    /// Get network statistics for a gvproxy instance
43    ///
44    /// Returns a JSON string containing network statistics including:
45    /// - bytes_sent, bytes_received: Total bandwidth
46    /// - tcp.forward_max_inflight_drop: Packets dropped due to maxInFlight limit
47    /// - tcp.current_established: Active TCP connections
48    /// - tcp.failed_connection_attempts: Total connection failures
49    /// - tcp.retransmits: TCP segments retransmitted
50    /// - tcp.timeouts: RTO timeout events
51    ///
52    /// # Arguments
53    /// * `id` - Instance ID returned from gvproxy_create
54    ///
55    /// # Returns
56    /// Pointer to JSON string (must be freed with gvproxy_free_string), or NULL if:
57    /// - Instance doesn't exist
58    /// - VirtualNetwork not initialized yet
59    /// - Stats collection or serialization failed
60    ///
61    /// # Safety
62    /// - `id` must be a valid instance ID
63    /// - Returned pointer must be freed with gvproxy_free_string
64    /// - Do not use pointer after calling gvproxy_free_string
65    pub fn gvproxy_get_stats(id: c_longlong) -> *mut c_char;
66
67    /// Get the libgvproxy version string
68    ///
69    /// # Returns
70    /// Pointer to version string (must be freed with gvproxy_free_string)
71    pub fn gvproxy_get_version() -> *mut c_char;
72
73    /// Set the log callback function for routing gvproxy logs to Rust
74    ///
75    /// When set, Go's slog handler will call this callback for all log messages,
76    /// allowing integration with Rust's tracing system.
77    ///
78    /// # Arguments
79    /// * `callback` - Function pointer to Rust logging callback, or NULL to disable
80    ///
81    /// # Safety
82    /// The callback must be thread-safe and must not panic.
83    /// Pass NULL to restore default stderr logging.
84    pub fn gvproxy_set_log_callback(callback: *const c_void);
85
86}
87
88#[cfg(test)]
89mod tests {
90    use super::*;
91
92    #[test]
93    fn test_version() {
94        unsafe {
95            let version = gvproxy_get_version();
96            assert!(!version.is_null());
97            gvproxy_free_string(version);
98        }
99    }
100}